Sé que 'cruzar límites' al hacer una llamada JNI en Java es lento.
Sin embargo, quiero saber qué es lo que lo hace lento. ¿Qué hace la implementación jvm subyacente al hacer una llamada JNI que la hace tan lenta?
Sé que 'cruzar límites' al hacer una llamada JNI en Java es lento.
Sin embargo, quiero saber qué es lo que lo hace lento. ¿Qué hace la implementación jvm subyacente al hacer una llamada JNI que la hace tan lenta?
Respuestas:
Primero, vale la pena señalar que "lento", estamos hablando de algo que puede llevar decenas de nanosegundos. Para los métodos nativos triviales, en 2010 medí las llamadas a un promedio de 40 ns en mi escritorio de Windows y 11 ns en mi escritorio de Mac. A menos que esté haciendo muchas llamadas, no lo notará.
Dicho esto, llamar a un método nativo puede ser más lento que hacer una llamada a un método Java normal. Las causas incluyen:
Se puede encontrar una discusión adicional, posiblemente fechada, en "Java¿ Platform Performance: Strategies and Tactics", 2000, de Steve Wilson y Jeff Kesselman, en la sección "9.2: Examen de los costos de JNI". Es aproximadamente un tercio del camino hacia abajo en esta página , proporcionado en el comentario de @Philip a continuación.
El documento de 2009 de IBM developerWorks "Mejores prácticas para usar la interfaz nativa de Java" proporciona algunas sugerencias para evitar dificultades de rendimiento con JNI.
sun.misc.Unsafe
y muchas otras cosas como System.currentTimeMillis/nanoTime
son manejadas a través de 'magia' por la JVM. No son JNI y no tienen los archivos .c / .h adecuados, dejando al descubierto el JVM impl. El enfoque no puede seguirse a menos que esté escribiendo / pirateando la JVM.
Vale la pena mencionar que no todos los métodos Java marcados con native
son "lentos". Algunos de ellos son intrínsecos que los hacen extremadamente rápidos. Para verificar cuáles son intrínsecos y cuáles no, puede buscar do_intrinsic
en vmSymbols.hpp .
Básicamente, la JVM construye interpretativamente los parámetros C para cada llamada JNI y el código no está optimizado.
Hay muchos más detalles descritos en este documento.
Si está interesado en comparar el JNI con el código nativo, este proyecto tiene código para ejecutar puntos de referencia.