起因

今天在写东西的时候,用到了多线程。遇到了个问题:

子线程的异常,在父线程中无法捕获。

解决

问题代码

问题代码示例代码如下:

import threading

class SampleThread(threading.Thread):
def run(self):
raise Exception('An error occured here.') def main():
try:
thread_obj = SampleThread()
thread_obj.start()
except Exception:
print 'catch that' if __name__ == '__main__':
main()

运行输出结果如下:

Exception in thread Thread-1:
Traceback (most recent call last):
File "/path/threading.py", line 810, in __bootstrap_inner
self.run()
File "/PycharmProjects/example/threading_example.py", line 15, in run
raise Exception('An error occured here.')
Exception: An error occured here.

解决办法

通过查看资料:http://stackoverflow.com/questions/2829329/catch-a-threads-exception-in-the-caller-thread-in-python

出现上述问题是因为:执行到 thread_obj.start() 时,父线程就会立即返回结果。然后,生成的子线程在自己独立的上下文中执行,并使用自己的堆栈。子线程发生的任何异常都是在子线程的上下文中,并且它在它自己的堆栈中(独立于父线程)。

所以,解决办法是:将这些信息传递给父线程。代码如下:

import sys
import threading
import Queue class ExcThread(threading.Thread): def __init__(self, bucket):
threading.Thread.__init__(self)
self.bucket = bucket def run(self):
try:
raise Exception('An error occured here.')
except Exception:
self.bucket.put(sys.exc_info()) def main():
bucket = Queue.Queue()
thread_obj = ExcThread(bucket)
thread_obj.start() while True:
try:
exc = bucket.get(block=False)
except Queue.Empty:
pass
else:
exc_type, exc_obj, exc_trace = exc
# deal with the exception
print exc_type, exc_obj
print exc_trace thread_obj.join(0.1)
if thread_obj.isAlive():
continue
else:
break if __name__ == '__main__':
import sys
import threading
import Queue class ExcThread(threading.Thread):
def __init__(self, bucket):
super(ExcThread, self).__init__()
self.bucket = bucket def run(self):
try:
raise Exception('An error occured here.')
except Exception:
# 异常信息元祖放入队列传递给父进程
self.bucket.put(sys.exc_info()) def main():
bucket = Queue.Queue()
thread_obj = ExcThread(bucket)
thread_obj.start() # 循环获取子线程的异常信息
while 1:
try:
exc = bucket.get(block=False)
except Queue.Empty:
pass
else:
exc_type, exc_obj, exc_trace = exc
# deal with the exception
print exc_type, exc_obj
print exc_trace # 防止阻塞
thread_obj.join(0.1)
if thread_obj.isAlive():
continue
else:
break if __name__ == '__main__':
main()

参考

[Python]获取子线程异常信息的更多相关文章

  1. python使用traceback获取详细的异常信息

    原创来自:https://blog.csdn.net/mengtao0609/article/details/55049059 python使用traceback获取详细的异常信息 2017年02月1 ...

  2. Java并发-UncaughtExceptionHandler捕获线程异常信息并重新启动线程

    Java并发-UncaughtExceptionHandler捕获线程异常信息并重新启动线程 一.捕获异常并重新启用线程 public class Testun { public static voi ...

  3. ARTS-S 获取子线程返回值注意事项

    #include <stdio.h> #include <stdlib.h> #include <pthread.h> #include <unistd.h& ...

  4. python获取系统内存占用信息的实例方法

    psutil是一个跨平台库(http://code.google.com/p/psutil/),能够轻松实现获取系统运行的进程和系统利用率(包括CPU.内存.磁盘.网络等)信息.它主要应用于系统监控, ...

  5. python主线程捕获子线程异常

    python内置threading.Thread类创建的子线程抛出的异常无法在主线程捕获,可以对该类进行优化,为子线程添加exit code属性,主线程通过获取子线程的返回状态,来判断子线程中是否发生 ...

  6. python多线程获取子线程任务返回值

    今天想实现多线程更新资产信息,所以使用到了threading,但是我需要每个线程的返回值,这就需要我在threading.Thread的基础上进行封装 def auto_asset(node): re ...

  7. 黄聪:WordPress 多站点建站教程(四):获取子站点相关信息(站点的注册时间,修改时间,总文章数,URL等)

    1.获取子站点blogs表里面的内容信息 $blog_details = get_blog_details(1); echo 'Blog '.$blog_details->blog_id.' i ...

  8. Android利用Handler异步获取子线程中的产生的值

        本文首发于cartoon的博客     转载请注明出处:https://cartoonyu.github.io/cartoon-blog     近段时间有一个需求:在线获取图片并且显示在界面 ...

  9. python 获取淘宝商品信息

    python cookie 获取淘宝商品信息 # //get_goods_from_taobao import requests import re import xlsxwriter cok='' ...

随机推荐

  1. java中关于转义字符的一个bug

    在java中,你可以定义 char c = '\u4f60'; char m = '\u0045'; char e = '\u554a'; 这样的字面量,例如: System.out.println( ...

  2. wpf后置代码中的Grid布局以及图片路径的设置

    之前用Grid练习连连看布局时,遇到了几个困惑.此次就把当时的一些收获写出来,供以后翻看. 图片路径可能比较常用,所以就写在第一个了. 在xaml中,设置图片非常简单,只要把图片拷贝到资源目录(这里假 ...

  3. HTML学习二

    继续上一次的学习: <html> <head> <title>新增雇员</title> <script language="javasc ...

  4. 单点登录实现(spring session+redis完成session共享)

    一.前言 项目中用到的SSO,使用开源框架cas做的.简单的了解了一下cas,并学习了一下 单点登录的原理,有兴趣的同学也可以学习一下,写个demo玩一玩. 二.工程结构 我模拟了 sso的客户端和s ...

  5. 前端学PHP之日期与时间

    前面的话 在Web程序开发时,时间发挥着重要的作用,不仅在数据存储和显示时需要日期和时间的参与,好多功能模块的开发,时间通常都是至关重要的.网页静态化需要判断缓存时间.页面访问消耗的时间需要计算.根据 ...

  6. JSP-表单元素示例

    <%@ page language="java" pageEncoding="UTF-8"%><%@ page import="ja ...

  7. Apache Struts2存在S2-045

    麻蛋的,批了老半天都找不到,还得谷歌 不扯蛋了,直接主题: Struts2 2.3.32 版本 下载地址:https://dist.apache.org/repos/dist/release/stru ...

  8. C#-MVC开发微信应用(1)--开始使用微信接口

    1.微信账号 要开发使用微信的平台API,就需要到微信的公众平台(https://mp.weixin.qq.com/)去注册,拥有一个服务号或者订阅号,服务号主要面对企业和组织,订阅号主要面向组织和个 ...

  9. 基于Struts自定义MVC-1

    自定义MVC        数据库:Oracle表:User(id,uname,upwd)自定义Struts框架一.定义Action接口 1 import javax.servlet.http.*; ...

  10. asp.net core mvc剖析:mvc动作选择

    一个http请求过来后,首先经过路由规则的匹配,找到最符合条件的的IRouter,然后调用IRouter.RouteAsync来设置RouteContext.Handler,最后把请求交给RouteC ...