2009-06-13 111 views
20

我正在用C#編寫一個自定義類,如果人們在某些方法中給出錯誤的輸入,我會拋出一些例外。如果拋出異常,拋出後方法中的任何代碼是否仍然會被執行?在投擲之後我是否必須休息一下,還是一定要拋出這個方法?拋出異常後我必須打破嗎?

+1

將其分解爲三個問題。 (1)拋出後的方法中的任何代碼是否會被執行?是。如果異常是在try中,那麼匹配catch塊或finally塊中的代碼將被執行。如果沒有嘗試塊,則沒有。控制最後分支到最近的包圍,捕獲或(在vb中)異常過濾塊阻止堆棧。 – 2009-06-13 15:11:59

+2

(2)投擲後我必須休息嗎?不,不要那樣做。 throw語句的結束點不可訪問;一個throw被編譯器視爲goto。緊跟在一個throw之後的語句不可達,並且永遠不會執行。 – 2009-06-13 15:13:02

+1

(3)拋出是否總是退出該方法?沒有。如果投擲是在嘗試中,並且嘗試有一個匹配的catch塊,那麼catch塊可以「吃」這個異常。只有在沒有catch塊的情況下,異常纔會執行非本地的調用堆棧。 – 2009-06-13 15:13:58

回答

30

當您的throw出現異常時,下一個要執行的代碼是覆蓋該方法(如果有)的任何catch代碼塊,然後是finally block(如果有的話)。你可以嘗試一下,嘗試一下,最後嘗試一下,或者試一試。然後,如果沒有處理異常,由catch塊重新拋出或根本沒有捕獲異常,則控制返回給調用者。例如,你會得到「支持1,YES2,是3」從這個代碼...

try 
{ 
    Console.WriteLine("Yes1"); 
    throw (new Exception()); 
    Console.WriteLine("No1"); 

} 
catch 
{ 
    Console.WriteLine("Yes2"); 
    throw; 
    Console.WriteLine("No2"); 
} 
finally 
{ 
    Console.WriteLine("Yes3"); 
} 

Console.WriteLine("No3"); 
27

拋出將向上移動堆棧,從而退出該方法。

1

如果你已經包裹在一個嘗試你的代碼... CATCH ... finally塊,然後根據代碼最終將永遠執行。例如:

Try 
    ' do some stuff here 
    ' Examine user input 
    If user input isn't valid 
     Throw new exception 
Catch 
    Throw ' Just re-throws the same exception 
Finally 
    ' This code will execute, no matter what - exception or not 
End Try 
1

順便到你的實際問題:你可能想用異常來提供驗證信息返回給用戶重新思考。

提高例外是昂貴的資源明智和緩慢。如果你有一些你需要應用的驗證規則,那麼就爲它們編寫特定的代碼 - 你應該僅僅依靠對你不期望的事情的異常處理。

3

我建議使用調試程序瀏覽您的程序,然後您會看到自己正在發生的事情。對學習非常有用!

2

我來到這裏尋找原帖的答案,幾乎錯過了Eric Lippert發佈的非常有價值的答案。以下是他在評論中發佈的答案:

將其分解爲三個問題。

(1)執行throw之後的方法中的任何代碼是否會被執行?
是的。如果異常是在try中,那麼匹配catch塊或finally塊中的代碼將被執行。如果沒有嘗試塊,則沒有。控制最後分支到最近的包圍,捕獲或(在vb中)異常過濾塊阻止堆棧。

(2)投擲後我必須休息嗎?
不,不要那樣做。 throw語句的結束點不可訪問;一個throw被編譯器視爲goto。緊跟在一個throw之後的語句不可達,並且永遠不會執行。

(3)一次拋出總是退出該方法嗎?
NO。如果投擲是在嘗試中,並且嘗試有一個匹配的catch塊,那麼catch塊可以「吃」這個異常。只有在沒有catch塊的情況下,異常纔會執行非本地的調用堆棧。

如果您對此有更多疑問,我建議您閱讀C#規範;所有這些行爲都有明確的記錄。

最後,這聽起來像是在拋出「骨頭頭」的異常,如「嘿骨頭打電話的人,我告訴過你永遠不要給我那些數據」。這很好,因爲它可以防止呼叫者中的錯誤。但是如果你這樣做,你應該確保調用者有一些方法來知道你的期望!如果調用者不能根據你的文檔判斷你是否要拋出,那麼你還沒有做出頭顱的例外,你已經做了一個令人煩惱的例外。詳情請參閱http://blogs.msdn.com/ericlippert/archive/2008/09/10/vexing-exceptions.aspx

相關問題