2011-04-12 29 views
0

我正在使用sql server 2005和.NET。 我有一個名爲「price」的浮動列表。 當我存放1890年它存儲1889.99966796875。sql存儲不同的值然後我存儲

是什麼原因?

+2

使用'money'作爲列類型。 – khachik 2011-04-12 13:58:18

+2

當我使用貨幣/貨幣來處理SQL Server和'System.Decimal'中的'Money'類型時,我相信你的值是'Money'。 – Johan 2011-04-12 14:14:26

回答

5

浮點數是一種特殊的數據類型,用於存儲變化範圍很大的數字。權衡是精確的 - 這就是你所看到的問題。 Floating point numbers

您可能想要用小數數據類型或金錢來存儲您的值。

+0

在.net中如何處理金錢和小數?我可以將它們加載到雙變量中嗎? – Naor 2011-04-12 14:10:33

+0

最好不要將它們視爲.Net中的雙打,否則您將遇到同樣的問題。 Money和Decimal SQL類型在.Net中被視爲Decimal。 – 2011-04-12 14:32:32

+0

小備註:權衡imho是準確性:不精確 – Peter 2011-04-12 19:27:50

3

浮動數字無法映射到所有數字的原因是因爲小數與分數之間的二進制系統不匹配。

1889.99966796875是在這個浮點域中最接近1890的數字,所以用這個二進制表示可以達到最接近的數字。

其他類型,如十進制和金錢,使用其他更多的內存消耗技術來存儲數字(例如,在一個字符串中可以存儲任何數字,但當然這不是最高性能的方式做數學)

一個簡單的例子:0.3在我自己的二元體系:

0.1b (inary) would be 0.5 d (ecimal) so too much... 
0.01b --> 0.25d (1/4 too little) 
0.011 --> 0.375 (1/4 + 1/8 too much) 
0.0101 --> 0.3125 (1/4 + 1/16 still too much) 
... 
0.010011 --> 1/4 +1/32 + 1/64 = 0.296875 

假設我的系統有6位表示分數,0.296875是最接近這個領域。由於十進制/二進制系統無法達到正確的編號。

有關示例見: Floating point inaccuracy examples

而且你的問題一個很好的精心explenation是在這裏找到: http://download.oracle.com/docs/cd/E19957-01/806-3568/ncg_goldberg.html

另注:這是真正關心的失配,而不是關於「質量」系統:例如,用十進制表示法,不能將1/3表示爲100%準確,而在其他系統中這是完全可能的。

2

任何您想要存儲精確數字或進行數學計算的數字都應該存儲爲十進制或數字不是浮點數。這是一種不精確的數據類型,它會導致舍入錯誤和不正確的計算。一般來說,浮動應該避免。

+0

這不是真的,fp是數學的第一位。例如。由於其他類型的性能損失,它通常用於統計中,因此您只需知道整個計算的準確性是否在預期的範圍內。 Fp不僅僅是在那裏使用它。 – Peter 2011-04-12 17:03:03

+0

對不起,除非你的數據太小(或者太小),否則float的四捨五入問題使它不適合數據庫中的數學運算。 – HLGEM 2011-04-12 17:48:45

+0

對不起,fp *在許多數學中正確使用它與大或小無關,但與重要數字無關。簡而言之:如果你需要5個和fp。正在提供10,正確使用的(應用的)操作完全沒有問題:舍入問題發生在有效數字之後,無論是在小數點之前還是之後。但對於離散數學,他們確實不適合。 – Peter 2011-04-12 19:24:47