Quiero realizar una variante de coincidencia de bloqueo de fuente anclada. Tengo definiciones de funciones que comienzan con una lista de nombres, y quiero que esos nombres se resalten dentro del cuerpo de la función.
Creé una función que hace esto y la registré como una función de bloqueo de jit con jit-lock-register, sin embargo, el rendimiento es bastante pobre y el desplazamiento se desplaza en archivos más grandes.
- ¿Cómo puedo medir el rendimiento? Si acabo de llamar a mi función en un archivo grande (con tiempo flotante antes y después o con elp) obtengo un rendimiento muy variable, toma de 0,65 a 12 segundos. ¿Hay alguna forma recomendada de evaluar el rendimiento del bloqueo de fuente?
- ¿Hay alguna diferencia en el rendimiento entre un emparejador anclado definido en font-lock-keywords y agregar una función a través de jit-lock-register?
Editar: Parece que la variabilidad en el rendimiento está relacionada con la recolección de basura, las invocaciones de mi función jit-lock se vuelven sucesivamente más lentas con cada invocación hasta que se ejecuta la recolección de basura, en cuyo punto se vuelven a acelerar.
font-lock
performance
Joakim Hårsman
fuente
fuente
Respuestas:
Resulta que el rendimiento muy variable estaba relacionado con la recolección de basura. Cada llamada a la función sería más lenta hasta que se ejecutara una recolección de basura. Con el stock emacs, gc se ejecutaba cada dos segundos, pero tenía una línea en mi init.el para mejorar el tiempo de inicio que establecía gc-cons-umbral en 20 MB, y eso significaba que gc se ejecutaba con mucha menos frecuencia, lo que causaba puntos de referencia para informe un tiempo cada vez más lento hasta que se ejecute un gc después de un par de minutos, luego los tiempos caerían en picado y volverían a ser rápidos.
Después de volver al valor predeterminado gc-cons-threshhold, la evaluación comparativa se hizo más fácil.
Luego perfilé la memoria con el generador de perfiles incorporado (
M-x profiler-start
), y descubrí que las llamadas a syntax-ppss causaban la mayoría de las asignaciones, por lo que después de alguna optimización para llamar a syntax-ppss con menos frecuencia logré un rendimiento aceptable.El uso de jit-lock-mode (agregar una función a través de jit-lock-register) parece ser la forma más fácil de lograr que el bloqueo de fuentes de varias líneas funcione de manera confiable, por lo que ese fue el método que elegí.
Editar: después de descubrir que el rendimiento aún no era lo suficientemente bueno en buffers muy grandes, pasé mucho tiempo optimizando el uso y la asignación de la CPU, midiendo las mejoras de rendimiento con el generador de perfiles Emacs incorporado (
M-x profiler-start
). Sin embargo, Emacs todavía tartamudearía y se colgaría al desplazarse rápidamente a través de buffers muy grandes. La eliminación de la función de bloqueo de jit con la que me registréjit-lock-register
eliminaría la tartamudez y los bloqueos, pero la creación de perfiles mostró que la función de bloqueo de jit se completa en alrededor de 8 ms, lo que debería ser lo suficientemente rápido para un desplazamiento suave. La eliminación de la llamadajit-lock-register
y, en su lugar, el uso de un emparejador de palabras clave de bloqueo de fuente regular resolvió el problema.TLDR: Hacer esto fue lento y tartamudearía:
Hacer esto fue rápido y no tartamudearía:
fuente
dyalog-fontify-locals
.dyalog-fontify-locals-matcher
debería sermy-font-lock-matcher
y uno de losend
debería serlimit
. De todos modos, ¡un descubrimiento realmente interesante!gc-cons-threshold
si estás jugando con valores internos únicamente para mejorar el tiempo de inicio, te sugiero que los usesemacs-startup-hook
para restaurarlos después.