2014-01-16 25 views
0

在MSDN和智能感知信息,沒有任何異常的記載調用Queue.Enqueue方法調用Queue.Enqueue方法

的時候會當什麼異常/錯誤可能發生但由於MSDN說

。 ....作爲元素添加到隊列時,容量被自動重新分配通過

需要我想這可以失敗,因爲沒有足夠的內存來保存新的元件增加。

當callin Queue.Enqueue方法有什麼其他錯誤可能發生? 也許答案可能包括一個鏈接到文件,列出所有的人都爲這個特殊的方法

我如何能趕上/處理OutOfMemoryException異常調用,即使不被拋出該方法是什麼時候?(即使我不能從內存不足錯誤中恢復我想記錄它)

並以「不甩」我的意思是

在任何方法的文檔總是提到的例外可能是什麼拋出該方法,但對於特定方法要麼沒有記錄,要麼不拋出任何異常。我想知道它是哪一個

+1

「即使它沒有被拋出」是什麼意思?如果沒有被拋出,沒有什麼可以抓到的。一般來說,如果你的進程內存不足,你不可能恢復... –

+0

@JonSkeet在任何方法的文檔中總是會提到該方法拋出的異常......對此特定的方法要麼沒有記錄,要麼id不會拋出任何異常 –

+0

您是否主要是Java程序員?如果是這樣,C#沒有相同的檢查異常概念 - 任何異常都可以從任何方法拋出,儘管文檔*可能*表示*可能*異常。同樣,你可以從任何代碼塊中捕獲任何類型的異常 - 編譯器不會抱怨! –

回答

1

這裏是排隊方法的拆裝(從ILSpy拍攝)

public void Enqueue(T item) 
{ 
    if (this._size == this._array.Length) 
    { 
     int num = (int)((long)this._array.Length * 200L/100L); 
     if (num < this._array.Length + 4) 
     { 
      num = this._array.Length + 4; 
     } 
     this.SetCapacity(num); 
    } 
    this._array[this._tail] = item; 
    this._tail = (this._tail + 1) % this._array.Length; 
    this._size++; 
    this._version++; 
} 

private void SetCapacity(int capacity) 
{ 
    T[] array = new T[capacity]; 
    if (this._size > 0) 
    { 
     if (this._head < this._tail) 
     { 
      Array.Copy(this._array, this._head, array, 0, this._size); 
     } 
     else 
     { 
      Array.Copy(this._array, this._head, array, 0, this._array.Length - this._head); 
      Array.Copy(this._array, 0, array, this._array.Length - this._head, this._tail); 
     } 
    } 
    this._array = array; 
    this._head = 0; 
    this._tail = ((this._size == capacity) ? 0 : this._size); 
    this._version++; 
} 

正如你所看到的,這是非常簡單的。你可以得到一個StackOverflowException,或OutOfMemoryException,因爲你可以總是潛在得到這些。

除此之外,還不清楚任何事情都可能出錯。您需要通過驗證代碼其餘部分中的各種檢查和保護子句來驗證是否存在NullPointerException的可能性,但粗略一眼顯示這可能不會發生。當然,如果你開始使用反射,你總是可以強制拋出一個NullPointerException異常。

我不知道這是否會對您有所幫助,但我相信它會回答您提出的問題。

0

看到你的編輯,這個問題更有意義。

MSDN文檔通常並沒有說明可以拋出OutOfMemoryException,基本上,任何方法調用都可以拋出它(任何分配內存的方法 - 幾乎都是這些方法!)。因此,你可以假設它可以在這種情況下拋出。


要使用捕捉異常弄清情況,可以想象這段代碼:

try 
    { 
     throw new ArgumentNullException(); 
    } 
    catch (ArgumentOutOfRangeException) 
    { 
     // This can never happen, but is perfectly legal code. 
    } 

catch塊將永遠不會被進入,但是編譯器是與此代碼完全滿意 - 它不會甚至發出警告。

+0

考慮問題的標題。我已經知道try/catch模式,但我正在尋找調用Enqueue時可能發生的可能錯誤 –

+0

文檔是正確的地方 - 但它不一定列出所有可能發生的異常(特別是對於可以被任何東西拋出,比如OutOfMemory或者StackOverflow)。這就是.NET的工作原理...... –

+0

我嘗試谷歌的其他可信任的地方,這可能會發現,但沒有運氣。但也許這是一個論壇張貼在那裏與我在找什麼。謝謝 –

0

如果你唯一的目標是捕獲所有可能的執行並記錄它們,並且別的什麼都不做,它實際上很簡單。

try 
{ 
    queue.Enqueue(foo); 
} 
catch (Exception ex) 
{ 
    LoggingMethod(ex); 
    throw; 
} 

什麼,將要做的就是趕上是可能捕獲所有異常(內存不足是,你可能不能夠爲數不多),記錄它,然後同時保留原來的堆棧跟蹤重新拋出異常所以這段代碼所在的代碼可以在必要時處理它。

throw ex;,導致在你的throw ex線被重新創建,以點堆棧跟蹤,你不知道哪一行代碼真正的異常被拋出從。

+1

Scott Chamberlain我唯一的目標不僅僅是捕捉任何錯誤,而是要了解當callin Enqueue方法發生什麼錯誤並嘗試處理它們時。也許鏈接到這是記錄 –