Pelampung 32-bit memiliki mantra 23 bit .
Itu berarti setiap angka direpresentasikan sebagai 1.xxx xxx xxx xxx xxx xxx xx kali beberapa kekuatan 2, di mana setiap x adalah digit biner, baik 0 atau 1. (Dengan pengecualian dari angka denormalized sangat kecil kurang dari 2- 126 - mereka mulai dengan 0. bukannya 1., tapi saya akan mengabaikannya untuk yang berikut)
Jadi dalam rentang dari 2saya dan 2( I + 1 ) , Anda dapat mewakili angka berapa pun dalam akurasi ± 2( i - 24 )
Sebagai contoh, untuk i = 0 , angka terkecil dalam kisaran ini adalah ( 20) ⋅ 1 = 1 . Angka terkecil berikutnya adalah ( 20) ⋅ ( 1 + 2- 23) . Jika Anda ingin mewakili 1 + 2- 24 , Anda harus membulatkan ke atas atau ke bawah, untuk kesalahan 2- 24 .
In this range: You get accuracy within:
-----------------------------------------------
0.25 - 0.5 2^-26 = 1.490 116 119 384 77 E-08
0.5 - 1 2^-25 = 2.980 232 238 769 53 E-08
1 - 2 2^-24 = 5.960 464 477 539 06 E-08
2 - 4 2^-23 = 1.192 092 895 507 81 E-07
4 - 8 2^-22 = 2.384 185 791 015 62 E-07
8 - 16 2^-21 = 4.768 371 582 031 25 E-07
16 - 32 2^-20 = 9.536 743 164 062 5 E-07
32 - 64 2^-19 = 1.907 348 632 812 5 E-06
64 - 128 2^-18 = 0.000 003 814 697 265 625
128 - 256 2^-17 = 0.000 007 629 394 531 25
256 - 512 2^-16 = 0.000 015 258 789 062 5
512 - 1 024 2^-15 = 0.000 030 517 578 125
1 024 - 2 048 2^-14 = 0.000 061 035 156 25
2 048 - 4 096 2^-13 = 0.000 122 070 312 5
4 096 - 8 192 2^-12 = 0.000 244 140 625
8 192 - 16 384 2^-11 = 0.000 488 281 25
16 384 - 32 768 2^-10 = 0.000 976 562 5
32 768 - 65 536 2^-9 = 0.001 953 125
65 536 - 131 072 2^-8 = 0.003 906 25
131 072 - 262 144 2^-7 = 0.007 812 5
262 144 - 524 288 2^-6 = 0.015 625
524 288 - 1 048 576 2^-5 = 0.031 25
1 048 576 - 2 097 152 2^-4 = 0.062 5
2 097 152 - 4 194 304 2^-3 = 0.125
4 194 304 - 8 388 608 2^-2 = 0.25
8 388 608 - 16 777 216 2^-1 = 0.5
16 777 216 - 33 554 432 2^0 = 1
Jadi, jika unit Anda adalah meter, Anda akan kehilangan presisi milimeter di sekitar 16 484 - 32 768 band (sekitar 16-33 km dari asal).
Secara umum diyakini Anda dapat mengatasi ini dengan menggunakan unit dasar yang berbeda, tetapi itu tidak benar, karena presisi relatif yang penting.
Jika kita menggunakan sentimeter sebagai unit kita, kita kehilangan ketelitian milimeter pada pita 1 048 576-2 097 152 (10-21 km dari asalnya)
Jika kami menggunakan hektametres sebagai unit kami, kami kehilangan presisi milimeter pada pita 128-256 (13-26 km dari titik asalnya)
... jadi mengubah unit lebih dari empat kali lipat masih berakhir dengan kehilangan presisi milimeter di suatu tempat di kisaran puluhan kilometer. Yang kami bergeser adalah di mana tepatnya di band itu hits (karena ketidakcocokan antara basis-10 dan basis-2 penomoran) tidak secara drastis memperluas area bermain kami.
Tepatnya seberapa banyak ketidaktepatan yang bisa ditoleransi permainan Anda akan tergantung pada detail gameplay Anda, simulasi fisika, ukuran entitas / jarak gambar, resolusi render, dll. Jadi sulit untuk menetapkan cutoff yang tepat. Mungkin rendering Anda terlihat baik-baik saja 50 km dari asalnya, tetapi peluru Anda berpindah melalui dinding, atau skrip gameplay yang sensitif menjadi berantakan. Atau Anda mungkin menemukan permainan ini berjalan dengan baik, tetapi semuanya memiliki getaran yang nyaris tidak terlihat dari ketidakakuratan dalam transformasi kamera.
Jika Anda mengetahui tingkat akurasi yang Anda butuhkan (katakanlah, rentang 0,01 unit peta hingga sekitar 1 px pada jarak pandang / interaksi khas Anda, dan offset yang lebih kecil tidak terlihat), Anda dapat menggunakan tabel di atas untuk menemukan di mana Anda kehilangan itu. akurasi, dan mundur beberapa urutan besarnya untuk keselamatan jika terjadi operasi yang merugi.
Tetapi jika Anda berpikir tentang jarak yang sangat jauh, mungkin lebih baik untuk menghindari semua ini dengan memasukkan kembali dunia Anda saat pemain bergerak. Anda memilih daerah berbentuk persegi atau kubus yang konservatif kecil di sekitar titik asal. Setiap kali pemain bergerak di luar wilayah ini, menerjemahkannya, dan semua yang ada di dunia, kembali setengah lebar dari wilayah ini, menjaga pemain tetap di dalam. Karena semuanya bergerak bersama, pemain Anda tidak akan melihat perubahan. Ketidakakuratan masih dapat terjadi di belahan dunia yang jauh, tetapi umumnya tidak terlalu terlihat di sana daripada terjadi tepat di bawah kaki Anda, dan Anda dijamin selalu memiliki ketepatan tinggi yang tersedia di dekat pemain.
Sulit untuk menjawab karena itu tergantung pada skala fisika Anda: Berapa kecepatan gerakan minimum yang dapat diterima yang TIDAK perlu dibulatkan menjadi nol?
Jika Anda membutuhkan dunia yang besar dan fisika yang konsisten, lebih baik menggunakan kelas poin tetap.
Misalnya, menembakkan bola meriam dari mana saja di dunia akan memberi Anda hasil yang sama dan titik tetap 64bit (32,32) memberi Anda ketepatan yang sangat besar dan lebih dari apa pun yang dapat dilihat di sebagian besar permainan. Jika unit Anda 1 meter Anda masih berada di 232 pikometer presisi 2147483km dari tempat asalnya.
Anda masih dapat melakukan fisika lokal dalam floating point dalam sel lokal untuk menghemat pekerjaan pemrograman dan menggunakan mesin fisika off-the-shelf. Ini akan tetap konsisten untuk semua tujuan praktis.
Sebagai fase bonus luas dan AABB cenderung lebih cepat di titik tetap karena latensi FPU. Ini juga lebih cepat untuk mengonversi titik tetap menjadi indeks octree (atau quadtree) karena Anda dapat melakukan masking bit sederhana.
Operasi-operasi itu tidak mendapatkan banyak manfaat dari instruksi SIMD dan pemipaan yang biasanya menyembunyikan latensi FPU.
Anda dapat mengubah posisi menjadi titik mengambang SETELAH mengurangi posisi kamera pada titik tetap untuk membuat semuanya, menghindari masalah titik mengambang di dunia besar dan masih menggunakan penyaji reguler menggunakan titik mengambang.
sumber
Anda dapat menghindarinya sekaligus dengan multiplikasi.
Alih-alih bekerja dengan float, cukup kalikan dengan 10 ^ (x), simpan, dan bila dibutuhkan, kalikan lagi dengan 10 ^ (- x).
Dari situ tergantung jenis int yang ingin Anda gunakan.
sumber