Un float a 32 bit ha una mantissa a 23 bit .
Ciò significa che ogni numero è rappresentato come 1.xxx xxx xxx xxx xxx xxx xxx xx volte una potenza di 2, dove ogni x è una cifra binaria, 0 o 1. (Ad eccezione di numeri denormalizzati estremamente piccoli inferiori a 2- 126 - iniziano con 0. anziché 1., ma li ignorerò per quanto segue)
Pertanto, nell'intervallo compreso tra 2io e 2( i + 1 ) , è possibile rappresentare qualsiasi numero con una precisione di ± 2( i - 24 )
Ad esempio, per i = 0 , il numero più piccolo in questo intervallo è ( 20) ⋅ 1 = 1 . Il numero più piccolo successivo è ( 20) ⋅ ( 1 + 2- 23) . Se si desidera rappresentare 1 + 2- 24 , è necessario arrotondare per eccesso o per difetto, per un errore di 2- 24 entrambi i modi.
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
Quindi, se le tue unità sono metri, perderai la precisione millimetrica attorno alla banda 16 484 - 32 768 (circa 16-33 km dall'origine).
Si ritiene comunemente che si possa aggirare questo problema utilizzando un'unità di base diversa, ma non è proprio vero, poiché è la precisione relativa che conta.
Se usiamo centimetri come nostra unità, perdiamo la precisione millimetrica nella banda 1 048 576-2 097 152 (10-21 km dall'origine)
Se usiamo ettometri come nostra unità, perdiamo la precisione millimetrica nella banda 128-256 (13-26 km dall'origine)
... quindi cambiare l'unità su quattro ordini di grandezza finisce ancora con una perdita di precisione millimetrica da qualche parte nel raggio di decine di chilometri. Tutto ciò che stiamo spostando è dove esattamente in quella banda colpisce (a causa della discrepanza tra la numerazione base-10 e base-2) non estendendo drasticamente la nostra area giocabile.
La precisione esatta che il tuo gioco può tollerare dipenderà dai dettagli del tuo gameplay, dalla simulazione fisica, dalle dimensioni delle entità / distanze di disegno, dalla risoluzione di rendering, ecc. Quindi è difficile stabilire un limite preciso. Forse il tuo rendering sembra a 50 km dall'origine, ma i tuoi proiettili si teletrasportano attraverso i muri o uno script di gameplay sensibile va in tilt. Oppure potresti trovare che il gioco funzioni bene, ma tutto ha una vibrazione appena percettibile a causa di imprecisioni nella trasformazione della videocamera.
Se conosci il livello di precisione di cui hai bisogno (ad esempio, un intervallo di 0,01 unità si mappa a circa 1 px alla tua distanza di visualizzazione / interazione tipica e qualsiasi offset più piccolo è invisibile), puoi utilizzare la tabella sopra per trovare dove lo perdi precisione e fare un passo indietro di alcuni ordini di grandezza per la sicurezza in caso di operazioni in perdita.
Ma se stai pensando a grandi distanze, potrebbe essere meglio eludere tutto ciò, aggiornando il tuo mondo mentre il giocatore si muove. Scegli una regione di forma quadrata o cubica conservativamente piccola attorno all'origine. Ogni volta che il giocatore si sposta al di fuori di questa regione, traducili e tutto il mondo, indietro di metà della larghezza di questa regione, mantenendo il giocatore dentro. Poiché tutto si muove insieme, il tuo giocatore non vedrà alcun cambiamento. Le imprecisioni possono ancora accadere in parti distanti del mondo, ma in genere sono molto meno evidenti lì che accadono proprio sotto i tuoi piedi, e hai la garanzia di avere sempre un'alta precisione disponibile vicino al giocatore.