Escribir Java de baja latencia [cerrado]


30

¿Existen técnicas específicas de Java (cosas que no se aplicarían a C ++) para escribir código de baja latencia en Java? A menudo veo roles de baja latencia de Java y piden experiencia escribiendo Java de baja latencia, lo que a veces parece un poco oxímoron.

Lo único que se me ocurre es la experiencia con JNI, subcontratando llamadas de E / S a código nativo. También es posible que use el patrón disruptor, pero esa no es una tecnología real.

¿Hay algún consejo específico de Java para escribir código de baja latencia?

Soy consciente de que hay una especificación Java en tiempo real, pero me han advertido que el tiempo real no es lo mismo que la baja latencia ...


no crear demasiados objetos que podrían desencadenar un ciclo de recogida sería mi conjetura
trinquete monstruo

@ratchet, supongo que cualquier cosa relacionada con la red o el disco también sería JNI.
user997112

Para obtener más enlaces y presentaciones, puede estar interesado en el Grupo de usuarios de Performance Java plus.google.com/u/1/communities/107178245817384004088
Peter Lawrey

Yo agregaría usando sun.misc.Unsafe, directa o indirectamente es útil. Muchos métodos inseguros se tratan como intrínsecos, lo que significa que se reemplazan con código de máquina, lo que evita cualquier JNI.
Peter Lawrey

La técnica principal es evitar por completo cualquier sobrecarga de GC. Puede leer más sobre eso en este artículo Desarrollo Java sin GC
rdalmeida

Respuestas:


35

Además de los comentarios de Martijn, agregaría:

  1. Calienta tu JVM. El inicio de código de bytes comienza siendo interpretado por Hotspot y luego se compila en el servidor después de 10K observaciones . La compilación escalonada puede ser una buena brecha.

  2. La carga de clases es un proceso secuencial que involucra IO en el disco. Asegúrese de que todas las clases para sus flujos de transacciones principales se carguen por adelantado y que nunca sean expulsadas de la generación permanente.

  3. Siga el " Principio del escritor único " para evitar disputas y las implicaciones del efecto de cola de la Ley de Little, además estudie la Ley de Amdhal para saber qué puede ser paralelo y si vale la pena.

  4. Modele su dominio comercial y asegúrese de que todos sus algoritmos sean O (1) o al menos O (log n). Esta es probablemente la mayor causa de problemas de rendimiento en mi experiencia. Asegúrese de tener pruebas de rendimiento para cubrir los casos principales.

  5. La baja latencia en Java no se limita solo a Java. Debe comprender toda la pila en la que se está ejecutando su código. Esto implicará el ajuste del sistema operativo, la selección del hardware apropiado, el software de los sistemas de ajuste y los controladores de dispositivo para ese hardware.

  6. Ser realista. Si necesita baja latencia, no se ejecute en un hipervisor. Asegúrese de tener suficientes núcleos para todos los subprocesos que deben estar en estado ejecutable.

  7. Los errores de caché son su mayor costo para el rendimiento. Utilice algoritmos que sean compatibles con la memoria caché y establezcan afinidad con los núcleos del procesador, ya sea con conjunto de tareas o numactl para un JVM o JNI para subprocesos individuales.

  8. Considere una JVM alternativa como Zing de Azul con un recolector de basura sin pausa.

  9. Lo más importante es involucrar a alguien con experiencia. Esto te ahorrará mucho tiempo a largo plazo. Enchufe descarado :-)

El tiempo real y la baja latencia son temas claramente separados, aunque a menudo están relacionados. El tiempo real se trata de ser más predecible que rápido. En mi experiencia, las JVM en tiempo real, incluso las suaves en tiempo real, son más lentas que las JVM normales.


2
+1 para una gran respuesta. Como alguien interesado en el procesamiento de mensajes de texto como este, es un excelente punto de partida para la investigación.
mcfinnigan

23

Hay un montón de cosas a tener en cuenta si. Estoy en Creta en este momento con acceso limitado a la red, así que esto será (bastante) corto. Además, no soy un experto en baja latencia, pero varios de mis colegas juegan uno en la vida real :-).

  1. Debes apreciar la simpatía mecánica (un término acuñado por Martin Thompson ). En otras palabras, debe comprender qué está haciendo su hardware subyacente. Es muy importante saber cómo las CPU cargan las líneas de caché, cuál es su ancho de banda de lectura / escritura, la velocidad de la memoria principal y mucho, mucho más. ¿Por qué? Porque necesitará razonar cómo su código fuente Java afecta el sistema operativo / hardware a través de la JVM de tiempo de ejecución. Por ejemplo, es la forma en que sus variables de campo se presentan en su código fuente causando desalojos de línea de caché (le cuesta ~ 150 ciclos de reloj), hmmm ... :-).

  2. En general, desea algoritmos y E / S sin bloqueo. Incluso la aplicación concurrente mejor diseñada (que usa bloqueos) está en riesgo de bloqueo, el bloqueo en baja latencia generalmente es malo :-).

  3. Comprender la asignación de objetos y la recolección de basura. Este es un tema masivo, pero básicamente desea evitar las pausas de GC (a menudo causadas por la naturaleza Stop the World de varias colecciones de GC). Los recolectores de GC especializados como el recolector Azul pueden en muchos casos resolver este problema de manera inmediata, pero para la mayoría de las personas necesitan entender cómo ajustar los GC de Sun / Oracle (CMS, G1, etc.).

  4. El Hotspot JIT es increíble. Aprenda acerca de sus optimizaciones, pero en general, todas las buenas técnicas de OO (encapsulación, métodos pequeños, tantos datos inmutables como sea posible) permitirán que JIT se optimice, dándole el tipo de niveles de rendimiento que le proporciona un código C / C ++ bien diseñado.

  5. Arquitectura general del sistema. Tenga en cuenta la red, cómo se ubican las máquinas, si está conectado al intercambio a través de fibra, etc.

  6. Tenga en cuenta el impacto de la tala. Probablemente sea una buena idea iniciar sesión en binario o usar una salida codificada que pueda analizar fuera de línea.

En general, recomiendo ir al curso de Java Performance Tuning de Kirk Pepperdine [Descargo de responsabilidad: enseño este curso yo mismo, así que soy parcial]. Obtendrá una buena cobertura de los diversos aspectos de la JVM y su impacto en la O / S subyacente y el hardware.

PD: Intentaré volver a visitar esto más tarde y ordenarlo un poco.


Sería realmente bueno si los experimentados con Simpatía Mecánica pudieran compartir algunos de los trucos para detectar cuándo se ha cruzado un límite determinado.

He pinchado en Twitter para tratar de obtener los verdaderos expertos en :-)
Martijn Verburg

Genial, Martin Thompson ha intervenido, vale la pena seguir sus consejos sobre los míos.
Martijn Verburg
Al usar nuestro sitio, usted reconoce que ha leído y comprende nuestra Política de Cookies y Política de Privacidad.
Licensed under cc by-sa 3.0 with attribution required.