问题:相当于e.printStackTrace的python

我知道print(e)(其中e是一个异常)会打印发生的异常,但是,我试图找到与Java等效的python,e.printStackTrace()它可以将异常确切地跟踪到发生的那一行,并打印出整个轨迹。

谁能告诉我e.printStackTrace()Python 的等效功能吗?

I know that print(e) (where e is an Exception) prints the occurred exception but, I was trying to find the python equivalent of Java’s e.printStackTrace() that exactly traces the exception to what line it occurred and prints the entire trace of it.

Could anyone please tell me the equivalent of e.printStackTrace() in Python?


回答 0

import traceback
traceback.print_exc()

在一个except ...:块内执行此操作时,它将自动使用当前异常。有关更多信息,请参见http://docs.python.org/library/traceback.html

import traceback
traceback.print_exc()

When doing this inside an except ...: block it will automatically use the current exception. See http://docs.python.org/library/traceback.html for more information.


回答 1

也有logging.exception

import logging

...

try:
    g()
except Exception as ex:
    logging.exception("Something awful happened!")
    # will print this message followed by traceback

输出:

ERROR 2007-09-18 23:30:19,913 error 1294 Something awful happened!
Traceback (most recent call last):
  File "b.py", line 22, in f
    g()
  File "b.py", line 14, in g
    1/0
ZeroDivisionError: integer division or modulo by zero

(摘自http://blog.tplus1.com/index.php/2007/09/28/the-python-logging-module-is-much-better-than-print-statements/通过如何打印完整的回溯而无需暂停程序?

There is also logging.exception.

import logging

...

try:
    g()
except Exception as ex:
    logging.exception("Something awful happened!")
    # will print this message followed by traceback

Output:

ERROR 2007-09-18 23:30:19,913 error 1294 Something awful happened!
Traceback (most recent call last):
  File "b.py", line 22, in f
    g()
  File "b.py", line 14, in g
    1/0
ZeroDivisionError: integer division or modulo by zero

(From http://blog.tplus1.com/index.php/2007/09/28/the-python-logging-module-is-much-better-than-print-statements/ via How to print the full traceback without halting the program?)


回答 2

相当于e.printStackTrace的python

在Java中,这将执行以下操作(docs):

public void printStackTrace()

将这个throwable及其回溯打印到标准错误流中。

这样使用:

try
{ 
// code that may raise an error
}
catch (IOException e)
{
// exception handling
e.printStackTrace();
}

在Java中,标准错误流没有缓冲,因此输出立即到达。

Python 2中的相同语义是:

import traceback
import sys
try: # code that may raise an error
    pass 
except IOError as e: # exception handling
    # in Python 2, stderr is also unbuffered
    print >> sys.stderr, traceback.format_exc()
    # in Python 2, you can also from __future__ import print_function
    print(traceback.format_exc(), file=sys.stderr)
    # or as the top answer here demonstrates, use:
    traceback.print_exc()
    # which also uses stderr.

Python 3

在Python 3中,我们可以直接从异常对象获取回溯(对于线程代码,其行为可能更好)。另外,stderr是行缓冲的,但是print函数获取flush参数,因此可以立即将其打印到stderr:

    print(traceback.format_exception(None, # <- type(e) by docs, but ignored 
                                     e, e.__traceback__),
          file=sys.stderr, flush=True)

结论:

因此,在Python 3中,traceback.print_exc()尽管sys.stderr 默认使用,但会缓冲输出,您可能会丢失它。因此,为了获得尽可能相等的语义,请在Python 3中print与一起使用flush=True

e.printStackTrace equivalent in python

In Java, this does the following (docs):

public void printStackTrace()

Prints this throwable and its backtrace to the standard error stream…

This is used like this:

try
{ 
// code that may raise an error
}
catch (IOException e)
{
// exception handling
e.printStackTrace();
}

In Java, the Standard Error stream is unbuffered so that output arrives immediately.

The same semantics in Python 2 are:

import traceback
import sys
try: # code that may raise an error
    pass 
except IOError as e: # exception handling
    # in Python 2, stderr is also unbuffered
    print >> sys.stderr, traceback.format_exc()
    # in Python 2, you can also from __future__ import print_function
    print(traceback.format_exc(), file=sys.stderr)
    # or as the top answer here demonstrates, use:
    traceback.print_exc()
    # which also uses stderr.

Python 3

In Python 3, we can get the traceback directly from the exception object (which likely behaves better for threaded code). Also, stderr is line-buffered, but the print function gets a flush argument, so this would be immediately printed to stderr:

    print(traceback.format_exception(None, # <- type(e) by docs, but ignored 
                                     e, e.__traceback__),
          file=sys.stderr, flush=True)

Conclusion:

In Python 3, therefore, traceback.print_exc(), although it uses sys.stderr by default, would buffer the output, and you may possibly lose it. So to get as equivalent semantics as possible, in Python 3, use print with flush=True.


回答 3

添加到其他伟大的答案,我们可以使用Python logging库的debug()info()warning()error(),和critical()方法。引用Python 3.7.4的文档,

在kwargs中检查了三个关键字参数:exc_info,如果不将其评估为false,则会将异常信息添加到日志消息中。

这意味着,您可以使用Python logging库输出debug()或其他类型的消息,并且该logging库将在其输出中包括堆栈跟踪。考虑到这一点,我们可以执行以下操作:

import logging

logger = logging.getLogger()
logger.setLevel(logging.DEBUG)

def f():
    a = { 'foo': None }
    # the following line will raise KeyError
    b = a['bar']

def g():
    f()

try:
    g()
except Exception as e:
    logger.error(str(e), exc_info=True)

它将输出:

'bar'
Traceback (most recent call last):
  File "<ipython-input-2-8ae09e08766b>", line 18, in <module>
    g()
  File "<ipython-input-2-8ae09e08766b>", line 14, in g
    f()
  File "<ipython-input-2-8ae09e08766b>", line 10, in f
    b = a['bar']
KeyError: 'bar'

Adding to the other great answers, we can use the Python logging library’s debug(), info(), warning(), error(), and critical() methods. Quoting from the docs for Python 3.7.4,

There are three keyword arguments in kwargs which are inspected: exc_info which, if it does not evaluate as false, causes exception information to be added to the logging message.

What this means is, you can use the Python logging library to output a debug(), or other type of message, and the logging library will include the stack trace in its output. With this in mind, we can do the following:

import logging

logger = logging.getLogger()
logger.setLevel(logging.DEBUG)

def f():
    a = { 'foo': None }
    # the following line will raise KeyError
    b = a['bar']

def g():
    f()

try:
    g()
except Exception as e:
    logger.error(str(e), exc_info=True)

And it will output:

'bar'
Traceback (most recent call last):
  File "<ipython-input-2-8ae09e08766b>", line 18, in <module>
    g()
  File "<ipython-input-2-8ae09e08766b>", line 14, in g
    f()
  File "<ipython-input-2-8ae09e08766b>", line 10, in f
    b = a['bar']
KeyError: 'bar'

声明:本站所有文章,如无特殊说明或标注,均为本站原创发布。任何个人或组织,在未征得本站同意时,禁止复制、盗用、采集、发布本站内容到任何网站、书籍等各类媒体平台。如若本站内容侵犯了原著者的合法权益,可联系我们进行处理。