Cómo usar timeit para perfilar el código Python

Por diseño, Python antepone la comodidad, la legibilidad y la facilidad de uso al rendimiento. Pero eso no significa que deba conformarse con un código Python lento. Probablemente haya algo que pueda hacer para acelerarlo.

Entre las herramientas disponibles para perfilar el rendimiento del código Python, la más simple es el timeitmódulo. timeitse utiliza para medir la velocidad de pequeños fragmentos de código (unas pocas líneas, una función) ejecutando el código miles o incluso millones de veces e informando cuánto tiempo tardaron esas ejecuciones en completarse.

timeites más útil para comparar dos o tres formas diferentes de hacer algo y ver cuál es la más rápida. Por ejemplo, un bucle que se ejecuta durante miles de iteraciones es un cuello de botella común de Python. Si puede encontrar una manera de acelerar la implementación de ese bucle, por ejemplo, utilizando elementos integrados de Python en lugar de código escrito a mano, podría obtener una mejora de rendimiento medible.

Un ejemplo simple de Python timeit

Aquí hay un ejemplo simple de cómo timeitfunciona:

def f1 (): para n en el rango (100): pasar def f2 (): n = 0 while n <100: n + = 1 if __name__ == "__main__": import timeit print (timeit.timeit (f1, number = 100000)) imprimir (timeit.timeit (f2, número = 100000)) 

Este programa compara el rendimiento de dos formas de iterar a través de un ciclo 100 veces: usando la función incorporada de Python  range ( f1) e incrementando una variable ( f2). timeit ejecuta cada uno de estos enfoques 100.000 veces y proporciona un tiempo de ejecución total al final de cada uno. De forma predeterminada,  timeit utiliza un millón de corridas, pero este ejemplo muestra cómo puede establecer el número de corridas en cualquier cifra que parezca apropiada.

Los resultados (de un procesador Intel i7-3770K):

0,1252315

0,45453989999999994

Claramente, el  range enfoque es mucho más rápido, en un factor de aproximadamente 3,75. Esto no es sorprendente; el uso de un Python incorporado generalmente produce un mejor rendimiento que la manipulación manual de objetos Python.

Use Python timeit pasando una cadena

Otra forma de uso  timeit es pasar una cadena que se evalúa como un programa de Python:

tiempo de importación

print (timeit.timeit ('para n en el rango (100): pass'))

Esto también se puede hacer desde la línea de comandos:

python -m timeit "para n en el rango (100): pasar"

En general, sin embargo, es más fácil usar la técnica que se muestra arriba, ya que no necesita calzar torpemente su código en una cadena de texto.

Consejos de Python Timeit

Tan útil como  timeit es, tenga en cuenta estas advertencias sobre cómo usarlo.

Evite utilizar timeit para la elaboración de perfiles de todo el programa

Nada dice que no se  pueda  cronometrar un programa completo  timeit. Un simple script de 10 líneas, por ejemplo, no es un mal candidato para ser perfilado de esta manera.

Pero existen mejores herramientas para ese trabajo, por ejemplo, el cProfile módulo de Python  , que genera estadísticas mucho más detalladas sobre el rendimiento de todo su programa. timeit funciona mejor con un solo componente o fragmento de código; de nuevo, una función o unas pocas líneas de código. Cualquier cosa más que eso generalmente generará resultados que son demasiado ruidosos e inconsistentes como para brindarle información significativa sobre el rendimiento.

Además, si el programa que está perfilando tarda muchos minutos en completarse,  timeit no será de mucha utilidad. Por un lado, llevará demasiado tiempo ejecutar el código más de unas pocas veces, por lo que los tiempos obtenidos serán muy crudos. Por dos, otras herramientas se adaptan mejor al trabajo.

Realice varias veces que se ejecute en diferentes máquinas

Los programas no se ejecutan siempre a la misma velocidad. Los entornos informáticos modernos presentan mucha incertidumbre: competencia con otros programas por recursos, comportamientos de caché, programación, etc. timeit intenta compensar esto ejecutando el código ad infinitum, pero sigue siendo una buena idea agregar varias pruebas. Debe ejecutar un  timeit perfil muchas veces, descartar las peores y mejores puntuaciones y promediar el resto.

Finalmente, también ayuda ejecutar la misma prueba en diferentes sistemas: ¿cómo se comportará algo vinculado a un disco en un SSD en comparación con un disco duro giratorio convencional? Al igual que con cualquier otra pregunta sobre el rendimiento, no adivine, pruebe.