Un enfoque empírico para garantizar el rendimiento de la API

Los programadores eligen las API, las estructuras de datos y las estructuras generales del programa en función de sus expectativas de rendimiento de las API. Si las expectativas o el rendimiento son muy incorrectos, el programador no puede recuperarse simplemente ajustando las llamadas a la API, sino que tiene que reescribir el programa (posiblemente partes importantes). La estructura defensiva del programa interactivo mencionado anteriormente es otro ejemplo.

Por supuesto, hay muchos programas cuya estructura y rendimiento rara vez se ven afectados por el rendimiento de la biblioteca (la informática científica y las grandes simulaciones a menudo entran en esta categoría). Sin embargo, gran parte de la "TI normal" actual, especialmente el software de los servicios basados ​​en web, hace un uso extensivo de bibliotecas que son fundamentales para el rendimiento general.

Incluso pequeños cambios en el rendimiento pueden provocar cambios importantes en la percepción que tiene el usuario de un programa, especialmente en programas que tratan con una variedad de medios. La pérdida ocasional de fotogramas de la transmisión de vídeo puede ser aceptable, pero los usuarios pueden percibir incluso ligeras interrupciones en el audio, por lo que pequeños cambios en el rendimiento de los medios de audio pueden tener un impacto significativo en la aceptabilidad del programa en general. Esta preocupación ha despertado un gran interés en la calidad del servicio, que en muchos sentidos consiste en garantizar altos niveles de rendimiento.

Aunque las violaciones de los contratos de desempeño son raras y rara vez catastróficas, prestar atención al desempeño cuando se utilizan bibliotecas de software puede ayudar a crear software más sólido. Aquí hay algunos principios empíricos:

1 Elija cuidadosamente la API y la estructura del programa

Si tiene la suerte de escribir un programa desde cero, piense en las implicaciones de los contratos de desempeño cuando comience a escribir su programa. Si el programa comienza como un prototipo y luego permanece en servicio por un tiempo, sin duda será reescrito al menos una vez; una reescritura es una oportunidad para repensar la API y las opciones arquitectónicas.

2 Proporcionar convenciones de rendimiento consistentes cuando se lanzan nuevas versiones.

Una nueva API experimental atraerá a usuarios que están empezando a derivar modelos de rendimiento de API. Después de eso, cambiar las convenciones de rendimiento seguramente irritará a los desarrolladores y posiblemente hará que reescriban sus programas. Una vez que la API madura, es importante que el contrato de desempeño siga siendo el mismo. De hecho, la mayoría de las API de propósito general (como libc) se han vuelto así en parte porque sus contratos de desempeño se han mantenido estables a lo largo de la evolución de la API. Lo mismo ocurre con el puerto API.

Se podría esperar que los proveedores de API prueben periódicamente nuevas versiones para verificar que no introduzcan peculiaridades en el rendimiento. Desafortunadamente, estas pruebas rara vez se realizan. Sin embargo, eso no significa que no puedas realizar tus propias pruebas en las partes dependientes de la API. Al utilizar un generador de perfiles, normalmente puede encontrar que un programa depende de una pequeña cantidad de API. Escribir una herramienta de prueba de rendimiento que compare el rendimiento registrado de una nueva versión de una API con versiones anteriores puede dar a los programadores una advertencia temprana de que el rendimiento de su propio código cambiará a medida que se publiquen nuevas versiones de la API.

Muchos programadores quieren que las computadoras y su software se vuelvan más rápidos con el tiempo. En realidad, esto es muy difícil de garantizar para el proveedor, pero convencerá al cliente de que así es. Muchos programadores esperan que las nuevas versiones de bibliotecas de gráficos, controladores y hardware mejoren el rendimiento de todas las aplicaciones gráficas y están entusiasmados con las mejoras en múltiples funciones, que a menudo reducen el rendimiento de funciones más antiguas, aunque sea ligeramente.

También podemos esperar que la especificación API haga explícito el contrato de desempeño, de modo que las personas que usan, modifican o portan el código puedan cumplir con el contrato. Tenga en cuenta que el uso de la asignación de memoria dinámica por parte de una función, ya sea implícita o automática, debe ser parte de la documentación de la API.

3 La programación defensiva puede ayudar

Los programadores pueden utilizar enfoques especiales al llamar a API cuyo rendimiento es desconocido o muy variable, especialmente cuando el rendimiento de fallas es una preocupación. Podemos mover la inicialización fuera de las áreas críticas para el rendimiento e intentar precargar cualquier dato almacenado en caché que la API pueda usar (como fuentes). Las API que presentan grandes diferencias de rendimiento o tienen grandes cantidades de datos almacenados en caché internamente pueden pasar sugerencias de la aplicación a la API proporcionando funciones auxiliares sobre cómo asignar o inicializar estas estructuras. Un programa que ocasionalmente hace ping a los servidores puede crear una lista de servidores potencialmente no disponibles, evitando tiempos de inactividad prolongados.

4 Ajuste de parámetros expuesto por API

Algunas bibliotecas proporcionan formas explícitas de afectar el rendimiento (por ejemplo, controlar el tamaño de los buffers asignados a los archivos, el tamaño inicial de las tablas o el tamaño de las cachés) y el sistema operativo también proporciona opciones de ajuste. Ajustar estos parámetros puede mejorar el rendimiento dentro de los límites de las convenciones de rendimiento; el ajuste no puede resolver el problema general, pero puede reducir las opciones fijas integradas en la biblioteca, lo que puede afectar seriamente el rendimiento.

Algunas bibliotecas proporcionan implementaciones alternativas de funciones con la misma semántica, generalmente implementaciones concretas de la API genérica. El ajuste eligiendo la mejor implementación concreta suele ser muy fácil y las colecciones de Java son un buen ejemplo de esta estructura.

Cada vez más, las API están diseñadas para adaptarse dinámicamente a la aplicación, liberando al programador de la necesidad de elegir la mejor configuración de parámetros. Si una tabla hash se llena demasiado, se extiende y se repite automáticamente (una ventaja, pero ocasionalmente un impacto en el rendimiento). Si el archivo se lee secuencialmente, se pueden asignar más buffers para leer en fragmentos más grandes.

5 Medición del desempeño para probar supuestos

Un enfoque común es instrumentar estructuras de datos críticas para determinar si cada estructura se está utilizando correctamente. Por ejemplo, puede medir qué tan completa está una tabla hash o con qué frecuencia ocurren colisiones hash. Alternativamente, es posible verificar que una estructura que es rápida de leer a expensas del rendimiento de escritura en realidad se lee con más frecuencia de la que se escribe.

Nada de esto tiene como objetivo impedir que los perfeccionistas desarrollen herramientas para automatizar paneles y mediciones, o que desarrollen métodos para detallar las convenciones de desempeño de modo que las mediciones de desempeño puedan establecer el cumplimiento de las convenciones de desempeño. Estos objetivos no serán fáciles de lograr y es posible que las recompensas no sean grandes.

Las mediciones de rendimiento a menudo se pueden realizar sin instrumentar primero el software, con la ventaja de que no se requiere trabajo antes de localizar un problema. También puede ayudar a diagnosticar problemas que surgen cuando los cambios en el código o las bibliotecas afectan el rendimiento. Ejecute perfiles de forma regular para medir las desviaciones de rendimiento de forma fiable.

6 Detectar y registrar anomalías mediante registros

Cuando los servicios distribuidos componen un sistema complejo, habrá cada vez más violaciones de los contratos de desempeño. Tenga en cuenta que los servicios proporcionados a través de interfaces de red a veces tienen acuerdos de nivel de servicio que especifican un rendimiento aceptable. En muchas configuraciones, el proceso de medición realiza solicitudes de servicio ocasionales para verificar que se cumplan los SLA. Dado que estos servicios utilizan métodos similares a las llamadas API (por ejemplo, llamadas a procedimientos remotos o sus variantes, como XML-RPC, SOAP o REST), pueden existir expectativas de contrato de desempeño. La aplicación detecta el fallo de estos servicios y suele responder adecuadamente.

Sin embargo, una capacidad de respuesta lenta, especialmente cuando hay muchos servicios de este tipo que dependen unos de otros, puede acabar con el rendimiento del sistema muy rápidamente. Sería útil si los clientes de estos servicios pudieran documentar el rendimiento que esperan y generar registros que ayuden a diagnosticar problemas (ese es uno de los usos de syslog). Cuando las copias de seguridad de archivos parecen excesivamente lentas, ¿son más lentas que ayer? ¿Más lento que antes de la última actualización del software del sistema operativo? ¿Es más lento de lo esperado dado que el dispositivo de respaldo puede ser compartido por varias computadoras? ¿O hay alguna explicación plausible (por ejemplo, el sistema de respaldo descubre una estructura de datos corrupta e inicia un largo proceso para reconstruirla)?

Diagnosticar problemas de rendimiento en composiciones de software opacas puede resultar útil para informar el rendimiento y encontrar problemas en ausencia de código fuente y detalles de los módulos y API que componen la composición. Si bien los problemas de rendimiento no se pueden resolver dentro del software, se pueden realizar ajustes o correcciones en el sistema operativo y la red. Si el dispositivo de respaldo es lento porque el disco está casi lleno, definitivamente agregue más espacio en el disco. Un buen registro y herramientas relacionadas ayudan; desafortunadamente, el registro puede ser un área infravalorada y descuidada en la evolución de los sistemas informáticos.

Es cierto que el contrato de desempeño es menos importante que el contrato de corrección funcional, pero casi toda la experiencia importante del usuario de un sistema de software depende de él.

Supongo que te gusta

Origin blog.csdn.net/Jernnifer_mao/article/details/132556614
Recomendado
Clasificación