En todos los lugares que he visto, dice que double
es superior float
en casi todos los sentidos. float
se ha vuelto obsoleto double
en Java, entonces ¿por qué todavía se usa?
float
Programo mucho con Libgdx, y te obligan a usar (deltaTime, etc.), pero me parece que double
es más fácil trabajar en términos de almacenamiento y memoria.
También leí ¿ Cuándo usas flotante y cuándo usas doble , pero si float
realmente solo es bueno para números con muchos dígitos después del punto decimal, entonces por qué no podemos usar una de las muchas variaciones de double
?
¿Hay alguna razón por la cual la gente insiste en usar flotadores a pesar de que ya no tiene ninguna ventaja? ¿Es demasiado trabajo cambiarlo todo?
java
memory
floating-point
numbers
Eames
fuente
fuente
byte
yshort
yint
cuando nolong
?Respuestas:
LibGDX es un marco utilizado principalmente para el desarrollo de juegos.
En el desarrollo de juegos, generalmente tienes que hacer muchos cálculos numéricos en tiempo real y cualquier rendimiento que puedas obtener es importante. Es por eso que los desarrolladores de juegos suelen usar flotante siempre que la precisión de flotación sea lo suficientemente buena.
El tamaño de los registros de FPU en la CPU no es lo único que debe tener en cuenta en este caso. De hecho, la mayor parte de la gran acumulación de números en el desarrollo del juego la realiza la GPU, y las GPU generalmente están optimizadas para flotadores, no para dobles .
Y luego también está:
que son recursos preciosos de los cuales obtienes el doble cuando usas flotante de 32 bits en lugar de doble de 64 bits.
fuente
Los flotadores usan la mitad de la memoria que los dobles.
Pueden tener menos precisión que los dobles, pero muchas aplicaciones no requieren precisión. Tienen un rango mayor que cualquier formato de punto fijo de tamaño similar. Por lo tanto, llenan un nicho que necesita amplios rangos de números pero que no necesita alta precisión, y donde el uso de memoria es importante. Los he usado para grandes sistemas de redes neuronales en el pasado, por ejemplo.
Al moverse fuera de Java, también se usan ampliamente en gráficos 3D, porque muchas GPU las usan como su formato principal; fuera de los dispositivos NVIDIA Tesla / AMD FirePro muy caros, el punto flotante de doble precisión es muy lento en las GPU.
fuente
Compatibilidad al revés
Esta es la principal razón para mantener el comportamiento en una ya existente lenguaje / biblioteca / ISA / etc.
Considere lo que sucedería si sacaran flotadores de Java. Libgdx (y miles de otras bibliotecas y programas) no funcionarían. Se necesitará mucho esfuerzo para actualizar todo, posiblemente años para muchos proyectos (solo mire la transición de Python 2 a Python 3 que rompe la compatibilidad con versiones anteriores). Y no todo se actualizará, algunas cosas se romperán para siempre porque los encargados del mantenimiento las abandonaron, tal vez antes de lo que lo harían porque requeriría más esfuerzo del que desean actualizar, o porque ya no es posible lograr lo que se suponía que su software suponía. que hacer.
Actuación
Los dobles de 64 bits ocupan el doble de memoria y casi siempre son más lentos de procesar que los flotantes de 32 bits (las excepciones muy raras son donde se espera que la capacidad de flotación de 32 bits se use tan raramente o nada, que no se hizo ningún esfuerzo para optimizarlos) A menos que esté desarrollando hardware especializado, no lo experimentará en el futuro cercano).
Especialmente relevante para ti, Libgdx es una biblioteca de juegos. Los juegos tienden a ser más sensibles al rendimiento que la mayoría del software. Y las tarjetas gráficas para juegos (es decir, AMD Radeon y NVIDIA Geforce, no FirePro o Quadro) tienden a tener un rendimiento de coma flotante de 64 bits muy débil. Cortesía de Anandtech, así es como el rendimiento de precisión doble se compara con el rendimiento de precisión simple en algunas de las principales tarjetas de juego de AMD y NVIDIA disponibles (a principios de 2016)
Tenga en cuenta que las series R9 Fury y GTX 900 son más nuevas que las series R9 200 y GTX 700, por lo que el rendimiento relativo para el punto flotante de 64 bits está disminuyendo. Regrese lo suficientemente lejos y encontrará el GTX 580, que tenía una relación de 1/8 como la serie R9 200.
1/32 del rendimiento es una penalización bastante grande a pagar si tienes una restricción de tiempo apretada y no ganas mucho usando el doble más grande.
fuente
Operaciones atómicas
Además de lo que otros ya han dicho, una desventaja específica de Java de
double
(ylong
) es que no se garantiza que las asignaciones a tipos primitivos de 64 bits sean atómicas . De la Especificación del lenguaje Java, Java SE 8 Edition , página 660 (énfasis agregado):Yuck
Para evitar esto, debe declarar la variable de 64 bits con la
volatile
palabra clave, o utilizar alguna otra forma de sincronización en torno a las asignaciones.fuente
Parece que otras respuestas omitieron un punto importante: las arquitecturas SIMD pueden procesar menos / más datos dependiendo de si operan
double
ofloat
estructuras (por ejemplo, ocho valores flotantes a la vez o cuatro valores dobles a la vez).Resumen de consideraciones de rendimiento
float
puede ser más rápido en ciertas CPU (por ejemplo, ciertos dispositivos móviles).float
usa menos memoria, por lo que en grandes conjuntos de datos puede reducir sustancialmente la memoria total requerida (disco duro / RAM) y el ancho de banda consumido.float
puede hacer que una CPU consuma menos energía (no puedo encontrar una referencia, pero si no es posible al menos parece plausible) para los cálculos de precisión simple en comparación con los cálculos de precisión doble.float
consume menos ancho de banda, y en algunas aplicaciones eso importa.float
usa tanto como la mitad de la memoria caché en comparación con el doble.Resumen de consideraciones de precisión
float
es suficientedouble
tiene mucha más precisión de todos modosConsideraciones de compatibilidad
double
(eso es porque los fabricantes de GPU intentan aumentar el número de núcleos gráficos, y Por lo tanto, intentan guardar la mayor cantidad de circuitos posible en cada núcleo, por lo que la optimizaciónfloat
permite crear GPU con más núcleos en el interior)double
como formato interno (para operaciones de renderizado 3D)Consejos generales
double
variables temporales en la pila proporciona precisión adicional de forma gratuita (precisión adicional sin penalización de rendimiento).float
, pero pueden ser valores limitados si está usandodouble
)float
o solodouble
ayuda enormemente al compilador a SIMD-ify las instrucciones.Vea los comentarios a continuación de PeterCordes para obtener más información.
fuente
double
los temporales solo son gratuitos en x86 con la x87 FPU, no con SSE2. Auto-vectorización de un bucle condouble
los temporales significa desembalajefloat
adouble
, que tiene una instrucción adicional, y procesar la mitad de los elementos por vectores. Sin la vectorización automática, la conversión generalmente puede ocurrir sobre la marcha durante una carga o almacenamiento, pero significa instrucciones adicionales cuando se mezclan flotantes y dobles en expresiones.Aparte de las otras razones que se mencionaron:
Si tiene datos de medición, ya sean presiones, flujos, corrientes, voltajes o lo que sea, esto a menudo se hace con hardware que tenga un ADC.
Un ADC generalmente tiene 10 o 12 bits, los de 14 o 16 bits son más raros. Pero sigamos con el de 16 bits: si mide alrededor de la escala completa, tiene una precisión de 1/65535. Eso significa que un cambio de 65534/65535 a 65535/65535 es solo este paso: 1/65535. Eso es aproximadamente 1.5E-05. La precisión de un flotador es de alrededor de 1E-07, por lo que es mucho mejor. Eso significa que no pierde nada al usar
float
para almacenar estos datos.Si hace cálculos excesivos con flotadores, tiene un rendimiento ligeramente peor que
doubles
en términos de precisión, pero a menudo no necesita esa precisión, ya que a menudo no le importa si solo midió un voltaje de 2 V o 2.00002 V. De manera similar , si convierte este voltaje en presión, no le importa si tiene 3 bar o 3.00003 bar.fuente