¿Cuándo debería usar la palabra clave “strictfp” en java?

He buscado lo que hace, pero ¿alguien realmente tiene un ejemplo de cuándo utilizaría la palabra clave strictfp en Java? ¿Alguien ha encontrado un uso para esto?

¿Habría algún efecto secundario de solo ponerlo en todas mis operaciones de coma flotante?

Strictfp garantiza que obtendrá exactamente los mismos resultados de sus cálculos de punto flotante en cada plataforma. Si no usa strictfp, la implementación de JVM es libre de usar precisión adicional donde esté disponible.

Desde el JLS :

Dentro de una expresión FP-strict, todos los valores intermedios deben ser elementos del conjunto de valores float o double value, lo que implica que los resultados de todas las expresiones FP-strict deben ser los predichos por aritmética IEEE 754 en operandos representados utilizando formatos simples y dobles . Dentro de una expresión que no es FP-estricta, se concede un margen para que una implementación use un rango de exponente extendido para representar resultados intermedios; el efecto neto, en términos generales, es que un cálculo puede producir “la respuesta correcta” en situaciones donde el uso exclusivo del conjunto de valores de flotación o el conjunto de valores dobles puede dar lugar a un desbordamiento o desbordamiento.

En otras palabras, se trata de asegurarse de que Write-Once-Run-Anywhere signifique en realidad Write-Once-Get-Equally-Wrong-Results-Everywhere .

Con strictfp sus resultados son portátiles, sin ellos es más probable que sean precisos.

Wikipedia en realidad tiene un buen artículo sobre este tema aquí , con un enlace a la especificación de Java.

Al leer entre líneas, la implicación es que si no especifica strictfp , entonces el comstackdor JVM y JIT tiene licencia para calcular sus cálculos de coma flotante como lo desee. En aras de la velocidad, lo más probable es que deleguen el cálculo en su procesador. Con strictfp on, los cálculos deben cumplir con los estándares aritméticos IEEE 754, lo que, en la práctica, probablemente signifique que la JVM realizará el cálculo.

Entonces, ¿por qué querrías usar strictfp ? Un escenario que puedo ver es en una aplicación distribuida (o juego multijugador) donde todos los cálculos de coma flotante deben ser deterministas sin importar cuál sea el hardware o CPU subyacente. ¿Cuál es la compensación? Probablemente el tiempo de ejecución.

Aquí hay varias referencias:

  • Uso de strictfp (JDC Tech Tip)
  • jGuru: ¿ Para qué sirve el modificador strictfp? ¿Cuándo consideraría usarlo?

    Básicamente, todo se reduce a si te preocupa que los resultados de las expresiones de coma flotante en tu código sean rápidos o predecibles. Por ejemplo, si necesita las respuestas de su código que utiliza valores de punto flotante para ser coherente en varias plataformas, utilice strictfp .

  • strictfp – Glosario de Java

    El hardware de coma flotante se calcula con más precisión y con un rango de valores mayor que el que requiere la especificación de Java. Sería confuso si algunas plataformas proporcionaran más precisión que otras. Cuando utiliza el modificador strictfp en un método o clase, el comstackdor genera código que se adhiere estrictamente a las especificaciones de Java para resultados idénticos en todas las plataformas. Sin strictfp , es ligeramente más laxo, pero no tan flojo como para usar los bits de protección en el Pentium para dar 80 bits de precisión.

  • Y, finalmente, la especificación del lenguaje de Java real, §15.4 Expresiones FP-estrictas :

    Dentro de una expresión FP-strict, todos los valores intermedios deben ser elementos del conjunto de valores float o double value, lo que implica que los resultados de todas las expresiones FP-strict deben ser los predichos por aritmética IEEE 754 en operandos representados utilizando formatos simples y dobles . Dentro de una expresión que no es FP-estricta, se concede un margen para que una implementación use un rango de exponente extendido para representar resultados intermedios; el efecto neto, en términos generales, es que un cálculo puede producir “la respuesta correcta” en situaciones donde el uso exclusivo del conjunto de valores de flotación o el conjunto de valores dobles puede dar lugar a un desbordamiento o desbordamiento.

Aunque nunca he tenido un uso personal para eso.

Todo comenzó con una historia,

Cuando java estaba siendo desarrollado por James Gosling, Herbert y el rest de su equipo. Tenían esta cosa loca en mente llamada independencia de la plataforma . Querían hacer que el roble (Java) fuera mucho mejor que cualquier otro equipo que tenga un conjunto de instrucciones diferente, incluso ejecutando diferentes sistemas operativos. Pero, hubo un problema con los números de punto decimal también conocido como punto flotante y doble en los lenguajes de progtwigción. Algunas máquinas se construyeron teniendo como objective la eficiencia mientras que el rest se enfocaba en la precisión. Entonces, las máquinas posteriores (más precisas) tenían un tamaño de punto flotante de 80 bits, mientras que las máquinas anteriores (más eficientes / más rápidas) tenían dobles de 64 bits. Pero, esto fue en contra de la idea central de construir un lenguaje independiente de plataforma. Además, esto puede conducir a la pérdida de precisión / datos cuando se crea un código en una máquina (que tiene el doble del tamaño de 64 bits) y se ejecuta en otro tipo de máquina (que tiene el doble de tamaño de 80 bits).

Se puede tolerar el aumento de tamaño, pero no se puede reducir el tamaño. Entonces, encontraron un concepto de strictfp, es decir, punto flotante estricto . Si usa esta palabra clave con una clase / función, su coma flotante y sus dobles tienen un tamaño constante en cualquier máquina. es decir, 32/64 bits, respectivamente.

Como las otras respuestas mencionadas causan que los resultados de punto flotante intermedio se ajusten a la especificación IEEE. En particular, los procesadores x86 pueden almacenar resultados intermedios con diferente precisión de la especificación IEEE. La situación se vuelve más complicada cuando el JIT optimiza un cálculo particular; el orden en que las instrucciones pueden ser diferentes cada vez resulta en un redondeo ligeramente diferente.

La sobrecarga incurrida por strictfp probablemente sea muy dependiente del procesador y JIT. Este artículo de Wikipedia sobre SSE2 parece tener una idea del problema. Entonces, si el JIT puede generar instrucciones de SSE para realizar un cálculo, parece que strictfp no tendrá ninguna sobrecarga.

En mi proyecto actual, hay algunos lugares donde utilizo strictfp. Hay un punto donde los rayos cósmicos potenciales deben ser eliminados de los valores de píxel. Si algún investigador externo tiene el mismo valor de píxel y el mismo rayo cósmico, deben obtener el mismo valor resultante que nuestro software.

  • strictfp es un modificador que restringe los cálculos de punto flotante según IEEE 754.

  • Esto se puede usar en toda la clase como “public strictfp class StrictFpModifierExample {}” o en el método “public strictfp void example ()”. Si se usa en clase, todos los métodos seguirán a IEEE 754 y si se usa en el método, entonces el método particular sigue IEEE 754.

  • Por qué se usa ??:: Como diferentes plataformas tienen hardware de coma flotante diferente que calcula con más precisión y un mayor rango de valores que la especificación java requiere, lo que puede producir una salida diferente en placas diferentes. Así que confirma la misma salida independientemente de la diferencia Placas

  • strictfp también garantiza aprovechar la velocidad y precisión de las operaciones de punto flotante de precisión extendida.

  • No hay desventaja con esta palabra clave que podemos usar cuando hacemos cálculos de punto flotante

  • Mi último punto es: ¿Qué es IEEE754 en resumen? IEEE 754 define el método estándar para cálculos de punto flotante y almacenamiento de valores de punto flotante en uno (32 bits, utilizado en flotantes Java) o doble (64 bits, utilizado en Java) dobla) precisión. También define normas para cálculos intermedios y para formatos de precisión extendidos.

strictfp es una palabra clave y se puede utilizar como un modificador que no sea de acceso para las clases o los métodos (pero nunca para las variables). Marcar una clase como strictfp significa que cualquier código de método en la clase se ajustará a las reglas estándar IEEE 754 para los puntos flotantes.

Sin ese modificador, los puntos flotantes utilizados en los métodos podrían comportarse de una manera dependiente de la plataforma. Con él puede predecir cómo se comportarán sus puntos flotantes independientemente de la plataforma subyacente en la que se esté ejecutando la JVM. La desventaja es que si la plataforma subyacente es capaz de soportar una mayor precisión, un método strictfp no podrá aprovecharla.

Si no declaras una clase como strictfp , aún puedes obtener el comportamiento strictfp método por método, declarando un método como strictfp .

~ Progtwigdor SCJP Sun®Certified para Java ™ 6 – Kathy Sierra y Bert Bates ~

A continuación, el ejemplo de ayuda ayuda a comprender esto más claro: en Java siempre que estamos buscando información precisa para cualquier operación, por ejemplo, si hacemos doble num1 = 10e + 102; doble num2 = 8e + 10; resultado = num1 + num2;

  The output will be so long and not precise, becasue it is precissed by the hardware eg JVM and JIT has the license as long as we dont have specify it Strictfp Marking it Strictfp will make the result Uniform on every hardware and platform, because its precised value will be same One scenario I can see is in a distributed application (or multiplayer game) where all floating-point calculations need to be deterministic no matter what the underlying hardware or CPU is.