Depurar multiprocesamiento en Python

Respuestas:

6

Programas Python cierto multiprocesamiento (en contraposición a múltiples rosca programas de Python que tienen que hacer frente a la temida GIL ) no son diferentes de las de cualquier otro idioma. Todos tienen los mismos desafíos básicos:

  1. Asignación de tareas e informes de resultados. Incluso si trabajan principalmente en conjuntos de datos independientes, normalmente tienen que volver al hilo maestro para informar los resultados y obtener nuevos datos para trabajar. Esto puede ser un punto de estrangulamiento.
  2. Condiciones de carrera. Los procesos están tratando de usar un recurso uno a la vez y necesitan usar mutex (o algo similar) para evitar pasar por encima de los datos del otro. No proteger este tipo de recursos puede llevar a sesiones de depuración realmente dolorosas.
  3. Secuencialidad A veces intentas hacer algo paralelo que no lo es. Los diversos procesos terminan esperando el uno al otro para hacer algo y el resultado final es que, para todos los efectos, ha tomado un programa secuencial, lo ha hecho paralelo y todavía termina ejecutándose en tiempo lineal (o peor).

Aunque existen métodos de desarrollo que intentan evitar cada uno de estos problemas, al final del día realmente necesita pensar en lo que está haciendo. Recomiendo pruebas de estrés intensas , mucho más allá de lo que crees que podría suceder en la vida real, para que tengas una buena oportunidad de alcanzar esas Ventanas de Oportunidad y explotar en el desarrollo en lugar de en medio de una demostración importante o durante la producción.

Solíamos usar archivos de registro con sello de tiempo de microsegundos y luego creamos una aplicación de visualización de registro codificada por colores para poder tratar de visualizar lo que sucedía entre el proceso N que se ejecuta en los procesadores M. También intentamos (y sobre todo lo logramos) crear un sistema que eliminara los archivos de registro para recrear el contexto del bloqueo.

Pero la mejor herramienta es un buen diseño y personas realmente malvadas y desagradables que intentan eliminar tu aplicación del agua. (Hola, Dbell!)

Peter Rowell
fuente
25

Una cosa que encuentro muy útil es usar el registrador existente en el multiprocessingmódulo. Prueba esto en tu código principal:

import multiprocessing, logging
mpl = multiprocessing.log_to_stderr()
mpl.setLevel(logging.INFO)

Ver también: http://docs.python.org/library/multiprocessing.html#logging

Además, puede acceder al nombre del proceso actual usando:

cpname = multiprocessing.current_process().name
# print cpname
mylogger.info("{0} is currently doing...".format(cpname))

Ver: http://docs.python.org/library/multiprocessing.html#multiprocessing.current_process

Aparte de eso, no sé nada más que los métodos de depuración estándar como pdb& co.

exhuma
fuente