<div class="blogpost-body" id="cnblogs_post_body">
<div>
<div>
<div class="article">
<div class="show-content">
<div class="show-content-free">
<p>刚接触Python的时候,简单的异常处理已经可以帮助我们解决大多数问题,但是随着逐渐地深入,我们会发现有很多情况下简单的异常处理已经无法解决问题了,如下代码,单纯的打印异常所能提供的信息会非常有限。</p>
<pre class="blockcode"><code class="language-python"><code class="python"><span class="hljs-function"><span class="hljs-keyword">def <span class="hljs-title">func1<span class="hljs-params">(): <span class="hljs-keyword">raise Exception(<span class="hljs-string">"--func1 exception--") <span class="hljs-function"><span class="hljs-keyword">def <span class="hljs-title">main<span class="hljs-params">(): <span class="hljs-keyword">try: func1() <span class="hljs-keyword">except Exception <span class="hljs-keyword">as e: <span class="hljs-keyword">print e <span class="hljs-keyword">if __name__ == <span class="hljs-string">'__main__': main() </span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></code></code></pre>
<p>执行后输出如下:</p>
<pre class="blockcode"><code class="language-php"><code class="php">--func1 <span class="hljs-keyword">exception--
</span></code></code></pre>
<p>通过示例,我们发现普通的打印异常只有很少量的信息(通常是异常的value值),这种情况下我们很难定位在哪块代码出的问题,以及如何出现这种异常。那么到底要如何打印更加详细的信息呢?下面我们就来一一介绍。</p>
<h3>sys.exc_info和traceback object</h3>
<p>Python程序的traceback信息均来源于一个叫做<strong>traceback object</strong>的对象,而这个traceback object通常是通过函数sys.exc_info()来获取的,先来看一个例子:</p>
<pre class="blockcode"><code class="language-python"><code class="python"><span class="hljs-keyword">import sys
<span class="hljs-function"><span class="hljs-keyword">def <span class="hljs-title">func1<span class="hljs-params">(): <span class="hljs-keyword">raise NameError(<span class="hljs-string">"--func1 exception--") <span class="hljs-function"><span class="hljs-keyword">def <span class="hljs-title">main<span class="hljs-params">(): <span class="hljs-keyword">try: func1() <span class="hljs-keyword">except Exception <span class="hljs-keyword">as e: exc_type, exc_value, exc_traceback_obj = sys.exc_info() <span class="hljs-keyword">print <span class="hljs-string">"exc_type: %s" % exc_type <span class="hljs-keyword">print <span class="hljs-string">"exc_value: %s" % exc_value <span class="hljs-keyword">print <span class="hljs-string">"exc_traceback_obj: %s" % exc_traceback_obj <span class="hljs-keyword">if __name__ == <span class="hljs-string">'__main__': main() </span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></code></code></pre>
<p>执行后输出如下:</p>
<pre class="hljs bash"><code class="bash">exc_type: <<span class="hljs-built_in">type <span class="hljs-string">'exceptions.NameError'>
exc_value: --func1 exception--
exc_traceback_obj: <traceback object at 0x7faddf5d93b0>
</span></span></code></pre>
<p>通过以上示例我们可以看出,sys.exc_info()获取了当前处理的exception的相关信息,并返回一个元组,元组的第一个数据是异常的类型(示例是NameError类型),第二个返回值是异常的value值,第三个就是我们要的traceback object.</p>
<p>有了traceback object我们就可以通过traceback module来打印和格式化traceback的相关信息,下面我们就来看下traceback module的相关函数。</p>
<h3>traceback module</h3>
<p>Python的traceback module提供一整套接口用于提取,格式化和打印Python程序的stack traces信息,下面我们通过例子来详细了解下这些接口:</p>
<h4>print_tb</h4>
<pre class="blockcode"><code class="language-python"><code class="python"><span class="hljs-keyword">import sys
<span class="hljs-keyword">import traceback
<span class="hljs-function"><span class="hljs-keyword">def <span class="hljs-title">func1<span class="hljs-params">(): <span class="hljs-keyword">raise NameError(<span class="hljs-string">"--func1 exception--") <span class="hljs-function"><span class="hljs-keyword">def <span class="hljs-title">main<span class="hljs-params">(): <span class="hljs-keyword">try: func1() <span class="hljs-keyword">except Exception <span class="hljs-keyword">as e: exc_type, exc_value, exc_traceback_obj = sys.exc_info() traceback.print_tb(exc_traceback_obj) <span class="hljs-keyword">if __name__ == <span class="hljs-string">'__main__': main() </span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></span></code></code></pre>
<p>输出:</p>
<pre class="blockcode"><code class="language- |
|