大家好,今天要講的是四捨五入。這個主題看似很簡單,但由於程式語言對於進位、捨去的實作標準跟我們以往學到的有所不同,使用四捨五入仍然要留意。
在 C# 和其它 .Net 語言環境中,使用 Math.Round()
進行四捨五入時,其結果未必與我們所熟悉的四捨五入相同。
Math.round(1.51) = 2
Math.round(1.5) = 2 // 會進位
Math.round(1.49)=1
Math.round(0.51) = 1
Math.round(0.5) = 0 // 不像一般四捨五入會進位
Math.round(0.49)=0
這是因為 .Net 遵循的是 IEEE Standard 754 第 4 節,其捨入方式可稱為:捨入至最接近值、四捨六入五成雙(Banker’s Rounding)
如果要對數值四捨五入的話,應在 Math.Round()
傳入參數 MidpointRounding.AwayFromZero
:
Math.round(0.5, MidpointRounding.AwayFromZero); // 結果為 1 (四捨五入)
參考資料: Round 真的是四捨五入嗎 - Jeff 隨手記 - 點部落
那麼,在 SQL 中又是如何實作的呢 ?
ROUND ( numeric_expression , length)
numeric_expression
為需要被捨入的數值,length 為捨入的位數。
例如:
ROUND(648.58, -1) -- 650.0
ROUND(23.994, 2) -- 23.99
如果對以下數值四捨五入,會產生溢位錯誤。
ROUND(0.5, 0) -- 預期為 1.0
出現錯誤 :
Msg 8115, Level 16, State 2, Line 2
轉換 expression 到資料類型 numeric 時發生算術溢位錯誤。
應該改成以下語法,事先轉型為 Numeric 或字串,才能正確取得結果:
SELECT ROUND(CAST(0.5 AS NUMERIC(2, 1)), 0)
SELECT ROUND('0.5', 0)
參考資料: