Aritmetik titik terapung

Selamat datang ke ansuran Under The Hood yang lain . Lajur ini bertujuan untuk memberi gambaran kepada para pengembang Java tentang keindahan tersembunyi di bawah program Java mereka yang sedang berjalan. Ruangan bulan ini meneruskan perbincangan, yang dimulakan bulan lalu, mengenai set arahan bytecode mesin maya Java (JVM). Artikel ini melihat aritmetik titik terapung di JVM, dan merangkumi kod byte yang melakukan operasi aritmetik titik terapung. Artikel seterusnya akan membincangkan ahli keluarga bytecode yang lain.

Titik terapung utama

Sokongan titik terapung JVM mematuhi standard titik terapung IEEE-754 1985. Piawaian ini menentukan format nombor terapung 32-bit dan 64-bit dan menentukan operasi pada nombor-nombor tersebut. Di JVM, aritmetik titik terapung dilakukan pada pelampung 32-bit dan ganda 64-bit. Untuk setiap kod bytec yang melakukan aritmetik pada apungan, terdapat kod bytek yang sesuai yang melakukan operasi yang sama pada ganda.

Nombor terapung mempunyai empat bahagian - tanda, mantissa, radix, dan eksponen. Tanda sama ada 1 atau -1. Mantissa, selalu nombor positif, menyimpan digit penting bagi nombor terapung. Eksponen menunjukkan daya positif atau negatif radix bahawa mantissa dan tanda harus dikalikan dengan. Keempat komponen digabungkan seperti berikut untuk mendapatkan nilai floating-point:

tanda * mantissa * eksponen radix

Nombor terapung mempunyai banyak perwakilan, kerana seseorang selalu dapat menggandakan mantissa sebarang nombor titik terapung dengan beberapa daya radix dan mengubah eksponen untuk mendapatkan nombor asal. Sebagai contoh, nombor -5 dapat ditunjukkan sama dengan salah satu bentuk berikut dalam radix 10:

Bentuk -5
Tanda Mantissa Eksponen Radix
-1 50 10 -1
-1 5 10 0
-1 0.5 10 1
-1 0.05 10 2

Untuk setiap nombor titik terapung ada satu representasi yang dikatakan dinormalisasi. Nombor terapung dinormalisasi jika mantissa berada dalam julat yang ditentukan oleh hubungan berikut:

1 / radix <= mantissa <

Nombor terapung radix 10 dinormalisasi mempunyai titik perpuluhannya di sebelah kiri digit bukan sifar pertama di mantissa. Perwakilan titik terapung normal -5 ialah -1 * 0.5 * 10 1. Dengan kata lain, mantissa nombor terapung dinormalisasi tidak mempunyai digit bukan sifar di sebelah kiri titik perpuluhan dan digit bukan sifar hanya untuk kanan titik perpuluhan. Setiap nombor terapung yang tidak masuk dalam kategori ini dikatakan dinormalisasi . Perhatikan bahawa angka sifar tidak memiliki representasi dinormalisasi, kerana ia tidak mempunyai digit bukan sifar untuk diletakkan tepat di sebelah kanan titik perpuluhan. "Mengapa dinormalisasi?" adalah seruan biasa di kalangan sifar.

Nombor terapung dalam JVM menggunakan jejari dua. Oleh itu, nombor terapung di JVM mempunyai bentuk berikut:

tanda * mantissa * 2 eksponen

Mantissa nombor terapung dalam JVM dinyatakan sebagai nombor binari. Mantissa yang dinormalisasi mempunyai titik perduaan (asas-dua bersamaan titik perpuluhan) di sebelah kiri digit bukan sifar yang paling signifikan. Kerana sistem nombor binari hanya mempunyai dua digit - sifar dan satu - digit yang paling signifikan dari mantissa yang dinormalisasi selalu satu.

Bit yang paling ketara dari float atau double adalah bit tanda. Mantissa menempati 23 bit terapung yang paling signifikan dan 52 bit ganda paling signifikan. Eksponen, 8 bit dalam pelampung dan 11 bit dalam dua kali ganda, terletak di antara tanda dan mantissa. Format float ditunjukkan di bawah. Bit tanda ditunjukkan sebagai "s", bit eksponen ditunjukkan sebagai "e", dan bit mantissa ditunjukkan sebagai "m":

Susun atur bit Java terapung
s eeeeeeee mmmmmmmmmmmmmmmmmmmmmmm

Bit tanda sifar menunjukkan nombor positif dan tanda bit satu menunjukkan nombor negatif. Mantissa selalu ditafsirkan sebagai nombor asas-dua positif. Ia bukan nombor pelengkap dua. Sekiranya bit tanda adalah satu, nilai floating-point adalah negatif, tetapi mantissa masih ditafsirkan sebagai nombor positif yang mesti didarabkan dengan -1.

Medan eksponen ditafsirkan dengan salah satu daripada tiga cara. Eksponen semua menunjukkan nombor titik terapung mempunyai salah satu nilai khas tambah atau tolak tak terhingga, atau "bukan nombor" (NaN). NaN adalah hasil operasi tertentu, seperti pembahagian sifar dengan sifar. Eksponen semua nol menunjukkan nombor titik terapung yang dinormalisasi. Mana-mana eksponen lain menunjukkan nombor titik apungan yang dinormalisasi

Mantissa mengandungi sedikit ketepatan tambahan daripada yang terdapat pada bit mantissa. Mantissa pelampung, yang hanya memuat 23 bit, mempunyai ketepatan 24 bit. Mantissa double, yang merangkumi 52 bit, mempunyai ketepatan 53 bit. Bit mantissa yang paling ketara dapat diramalkan, dan oleh itu tidak disertakan, kerana eksponen nombor titik terapung di JVM menunjukkan sama ada bilangannya dinormalisasi atau tidak. Sekiranya eksponen adalah semua nol, nombor titik terapung dinormalisasi dan bit mantissa yang paling ketara diketahui adalah sifar. Jika tidak, nombor floating-point dinormalisasi dan bit mantissa yang paling penting diketahui satu.

JVM tidak memberikan pengecualian akibat daripada operasi floating-point. Nilai khas, seperti infiniti positif dan negatif atau NaN, dikembalikan sebagai hasil operasi yang mencurigakan seperti pembahagian dengan sifar. Eksponen semua menunjukkan nilai titik apungan khas. Eksponen semua yang mempunyai mantissa yang bitnya semua sifar menunjukkan tak terhingga. Tanda infiniti ditunjukkan oleh bit tanda. Eksponen semua yang mempunyai mantissa lain ditafsirkan bermaksud "bukan nombor" (NaN). JVM selalu menghasilkan mantissa yang sama untuk NaN, yang semuanya nol kecuali bit mantissa yang paling ketara yang muncul dalam jumlahnya. Nilai-nilai ini ditunjukkan untuk pelampung di bawah:

Nilai apungan khas
Nilai Float bit (tanda eksponen mantissa)
+ Infiniti 0 11111111 00000000000000000000000
-Infiniti 1 11111111 00000000000000000000000
NaN 1 11111111 10000000000000000000000

Eksponen yang bukan semua atau nol menunjukkan kekuatan dua yang dapat melipatgandakan mantissa yang dinormalisasi. Kekuatan dua dapat ditentukan dengan menafsirkan bit eksponen sebagai nombor positif, dan kemudian mengurangkan bias dari nombor positif. Untuk apungan, bias adalah 126. Untuk gandaan, bias adalah 1023. Contohnya, medan eksponen dalam apungan 00000001 menghasilkan kekuatan dua dengan mengurangkan bias (126) dari medan eksponen yang ditafsirkan sebagai bilangan bulat positif (1). Oleh itu, kekuatan dua adalah 1 - 126, iaitu -125. Ini adalah kekuatan terkecil dua untuk apungan. Pada tahap ekstrem yang lain, medan eksponen 11111110 menghasilkan kekuatan dua dari (254 - 126) atau 128. Nombor 128 adalah kuasa terbesar dua yang tersedia untuk pelampung. Beberapa contoh apungan normal ditunjukkan dalam jadual berikut:

Nilai apungan dinormalisasi
Nilai Float bit (tanda eksponen mantissa) Eksponen yang tidak berpatutan
Terapung positif (terhingga) terbesar 0 11111110 11111111111111111111111 128
Terapung negatif (terhingga) terbesar 1 11111110 11111111111111111111111 128
Apungan normal terkecil 1 00000001 00000000000000000000000 -125
Pi 0 10000000 10010010000111111011011 2

Eksponen semua angka nol menunjukkan mantissa dinormalisasi, yang bermaksud bit pendahuluan yang tidak dinyatakan adalah sifar dan bukan satu. Kekuatan dua dalam kes ini adalah sama dengan kuasa terendah dua yang tersedia untuk mantissa yang dinormalisasi. Untuk apungan, ini adalah -125. Ini bermaksud bahawa mantissas dinormalisasi dikalikan dengan dua dinaikkan ke kekuatan -125 memiliki medan eksponen 00000001, sementara mantissas dinormalisasi dikalikan dengan dua dinaikkan ke -125 memiliki medan eksponen 00000000. akhir julat eksponen menyokong aliran masuk beransur-ansur. Sekiranya eksponen terendah digunakan untuk mewakili nombor yang dinormalisasi, aliran masuk ke sifar akan berlaku untuk bilangan yang lebih besar. Dengan kata lain, meninggalkan eksponen terendah untuk nombor denormalisasi membolehkan bilangan yang lebih kecil diwakili.Nombor denormalisasi yang lebih kecil mempunyai ketepatan bit yang lebih sedikit daripada nombor yang dinormalisasi, tetapi ini lebih baik daripada mengalir ke nol sebaik sahaja eksponen mencapai nilai normalisasi minimum.

Nilai apungan dinormalisasi
Nilai Float bit (tanda eksponen mantissa)
Terapung positif terkecil (bukan sifar) 0 00000000 00000000000000000000001
Terapung negatif (bukan sifar) terkecil 1 00000000 00000000000000000000001
Float denormalized terbesar 1 00000000 11111111111111111111111
Sifar positif 0 00000000 00000000000000000000000
Sifar negatif 1 00000000 00000000000000000000000

Terapung terdedah

Float Java menunjukkan sifat dalamannya. Applet di bawah ini membolehkan anda bermain-main dengan format floating-point. Nilai apungan dipaparkan dalam beberapa format. Format notasi saintifik radix dua menunjukkan mantissa dan eksponen dalam basis sepuluh. Sebelum dipaparkan, mantissa yang sebenarnya dikalikan dengan 2 24, yang menghasilkan nombor tidak terpadu, dan eksponen yang tidak berat sebelah dikurangkan dengan 24. Kedua-dua mantissa dan eksponen integral kemudiannya dengan mudah ditukar menjadi pangkalan sepuluh dan dipaparkan.