2010-05-29 30 views
33

這是怎麼回事?我做一個簡單的乘法:不應該導致溢出?它不!

Int64 x = 11111111111; 
Int64 y = 11111111111; 
Int64 z = x * y; 

,並在乘法結束,Z顯示的值:

-5670418394979206991

這顯然已經溢出,但不會引發異常。我想要一個被提出,但...

請注意,這是在Windows Phone 7上,但我不認爲這對此問題有任何影響。還是呢?

回答

43

您可以使用一個檢查塊作爲已指出其他答案:

checked 
{ 
    long x = 11111111111; 
    long y = 11111111111; 
    long z = checked(x * y); 
    // ... 
} 

導致異常:

發生OverflowException:算術運算導致溢出。

如果你只是在做你需要檢查你可以使用checked expression,而不是一個單一的操作:

long x = 11111111111; 
long y = 11111111111; 
long z = checked(x * y); 

您還可以設置/checked compiler option有默認的檢查。

設置在Visual Studio開發環境中,該編譯器選項:

  1. 打開項目的屬性頁對話框。有關詳情,請參閱Setting Visual C# Project Properties
  2. 單擊配置屬性文件夾。
  3. 點擊Build屬性頁。
  4. 修改檢查算術溢出/下溢屬性

如果更改默認選中,您可以使用選中塊或表達式來再次獲得未經檢查的行爲。

+25

請注意,未選中的原因是默認的原因是(1)99%的時間整數運算不在邊界附近,(2)檢查的算術運行速度較慢。這是C#設計出於性能原因選擇違約危險的罕見情況之一。 – 2010-05-29 15:36:51

+0

x86抖動使用簡單的jno,分支預測總是很好,不能超過單個週期。 – 2010-06-13 11:46:47

+0

並不是說它必然與C#的設計有關,但在這個特定情況下,我們正在討論ARM。 x86抖動的行爲有些學術性 – Stewart 2010-06-18 18:19:59

26

Check it

checked 
{ 
    Int64 x = 11111111111; 
    Int64 y = 11111111111; 
    Int64 z = x * y; 
} 
+6

賓果!每天學點新東西,我知道!謝謝。並且非常感謝SO。 – Cyberherbalist 2010-05-29 09:19:04

8

嘗試:

checked 
{ 
    Int64 x = 11111111111; 
    Int64 y = 11111111111; 
    Int64 z = x * y; 
} 
8

編譯器假設你想這樣做的,並與溢出繼續進行。如果需要將溢出視爲操作異常,請圍繞checked執行操作,並在運行時引發異常。

checked 
{ 
    Int64 x = 11111111111; 
    Int64 y = 11111111111; 
    Int64 z = x * y; 
} 

System.OverflowException:一個異常類型System.OverflowException的 是 拋出。