Quiero guardar el nombre del error y los detalles de rastreo en una variable. Aquí está mi intento.
import sys
try:
try:
print x
except Exception, ex:
raise NameError
except Exception, er:
print "0", sys.exc_info()[0]
print "1", sys.exc_info()[1]
print "2", sys.exc_info()[2]
Salida:
0 <type 'exceptions.NameError'>
1
2 <traceback object at 0xbd5fc8>
Salida deseada:
0 NameError
1
2 Traceback (most recent call last):
File "exception.py", line 6, in <module>
raise NameError
PD: Sé que esto se puede hacer fácilmente usando el módulo de rastreo, pero quiero saber el uso del objeto sys.exc_info () [2] aquí.
python
exception-handling
codificadores del oscuro
fuente
fuente
<python install path>/Lib/traceback.py
) para obtener más información.Respuestas:
Así es como lo hago:
Sin embargo, debe echar un vistazo a la documentación de rastreo , ya que puede encontrar métodos más adecuados, dependiendo de cómo desee procesar su variable después ...
fuente
sys.exc_info()[2].tb_frame.f_code.co_names[3]
, pero no tiene ningún sentido ... Si hay un módulo llamadotraceback
en la biblioteca estándar, hay una razón para ello ... :)traceback.format_exception(*sys.exc_info())
es la forma de hacerlo. Pero eso es funcionalmente equivalente atraceback.format_exc()
.sys.exc_info () devuelve una tupla con tres valores (tipo, valor, rastreo).
Por ejemplo, en el siguiente programa
Ahora, si imprimimos la tupla, los valores serán este.
Los detalles anteriores también se pueden obtener simplemente imprimiendo la excepción en formato de cadena.
fuente
Úselo
traceback.extract_stack()
si desea un acceso conveniente a los nombres de módulos y funciones y números de línea.Úselo
''.join(traceback.format_stack())
si solo desea una cadena que se parezca a latraceback.print_stack()
salida.Tenga en cuenta que incluso con
''.join()
usted obtendrá una cadena de varias líneas, ya que los elementos deformat_stack()
contienen\n
. Ver salida a continuación.Recuerde
import traceback
.Aquí está la salida de
traceback.extract_stack()
. Formato agregado para facilitar la lectura.Aquí está la salida de
''.join(traceback.format_stack())
. Formato agregado para facilitar la lectura.fuente
Tenga cuidado al sacar el objeto de excepción o el objeto de rastreo del manejador de excepciones, ya que esto causa referencias circulares y
gc.collect()
no se podrá recopilar. Esto parece ser un problema particular en el entorno portátil ipython / jupyter donde el objeto de rastreo no consigue aclaró en el momento adecuado, e incluso una llamada explícita agc.collect()
enfinally
la sección no hace nada. Y ese es un gran problema si tiene algunos objetos enormes que no recuperan su memoria debido a eso (p. Ej., Excepciones de CUDA sin memoria que sin esta solución requieren un reinicio completo del núcleo para recuperarse).En general, si desea guardar el objeto de rastreo, debe borrarlo de las referencias a
locals()
, así:En el caso del cuaderno jupyter, debe hacerlo al menos dentro del controlador de excepciones:
Probado con python 3.7.
ps el problema con ipython o jupyter notebook env es que tiene
%tb
magia que guarda el rastreo y lo hace disponible en cualquier momento posterior. Y como resultado, ningunolocals()
de los fotogramas que participan en el rastreo no se liberará hasta que el notebook salga u otra excepción sobrescribirá el rastreo almacenado anteriormente. Esto es muy problemático. No debe almacenar el rastreo sin limpiar sus marcos. Arreglo enviado aquí .fuente
El objeto se puede usar como parámetro en la
Exception.with_traceback()
función:fuente