Float計算機表示形式

float爲何比int表示的範圍廣?java

什麼是單精度和雙精度?數據庫

float表示小數的時候爲何會有精度丟失?函數

帶着這幾個問題,咱們來探究下javafloat類型在計算機的表示形式。ui

javaint佔用4個字節,float也是佔用4個字節,可是爲何float表示的範圍要比int大呢,由於二者在計算機內中表示的方式不同,int4個字節32位,每一位都是二進制小數表示,最高位0表明是正數,最高位爲1表明是負數,因此int的範圍是-2^31~2^31-1;spa

float也是4個字節,遵循IEEE-754格式標準,在計算機中表示有三個部分組成:符號s底數m和指數eci

 

符號s最高位,0爲正數;1爲負數,佔用一位;字符串

指數e是該浮點數的指數,二進制表示,最高位爲指數符號爲1表示大於10表示小於1其實他是用的偏移量表示的,偏移大小爲127,沒有用補碼錶示,佔用一個字節8rpc

底數m是該浮點數的實際值,二進制形式表示,m的範圍是【12】或者【01】佔用23位。it

因此float在計算機的表示以下面所示:io

SEEEEEEEEMMMMMMMMMMMMMMMMMMMMMMM

 

咱們先說下10進制和二進制的快速轉換方法。

10進制整數2進制轉換是除2求商和餘數,好比十進制17的二進制計算爲:

17 /2=161

16 /2= 8 0

8 /2= 4 0

4 /2= 2 0

2 /2= 1 0

1 /2= 0 1

一直計算到商爲0爲止,17的二進制表示就是:10001

 

10進制小數2進製表示是乘2求積,好比0.16的二進制計算爲:

0.16*2=0.320

0.32*2=0.640

0.64*2=1.281

0.28*2=0.560

0.56*2=1.121

0.12*2=0.240

。。。

因此0.16的二進制表示就是001010..... 一直循環下去,因此除非小數最後爲5才能*2取整,不然都會無線循環下去,這就是爲何浮點小數精度丟失的問題。

 

下面咱們距離來講明10進制浮點數在計算機的表示, 拿17.16來講:

1.首先爲正數,s0

2.二進制爲10001.0010100011110101....小數點左移4位爲1.00010010100011110101...

3.指數位爲4+127=10000011,因此指數位位10000011

4.因爲默認最左邊爲1,因此底數爲00010010100011110101...

5.最後17.16的二進制表示就是:01000001100010010100011110101......總共32位,後面的捨棄

 

再拿0.16舉例:

1.首先爲整數,s0

2.二進制爲0.0010100011110101......小數點右移4位爲1.0100011110101

3.指數位爲4+127=10000011,而後取反爲01111100,因此指數位位01111100

4.底數位0100011110101...

5.最後0.16的二進制表示就是:0011111000100011110101...

 

float的(正數)範圍:

最小值:Float.MIN_VALUE=1.4E-45 2-149次方:指數位127+底數22
最大值:Float.MAX_VALUE=3.4028235E38 2128次方-1

 

注意事項:

1.價格在數據庫中保存建議是無符號整形,避免在java轉換成浮點數時出現精度丟失的問題;

2.若是須要用浮點型數據進行運算,建議使用BigDecimal,可是BigDecimal的構造函數必定要使用字符串的,不然同樣會出現精度丟失的問題:BigDecimal(「123f」)而不是BigDecimal(123f)

3.Float.MIN_VALUE是:1.4E-45,不是一個負數,double也是的。可是整型的MIN_VALUE都是負數

4.floatm只有23位,2^23=8388608,總共有710進制數字,因爲最左邊的1省略了,因此表示的有效數字最高精確度位78位,包括整數部分,8位後的數字確定不是準確的

相關文章
相關標籤/搜索