这是我的问题Hang in Python script using SQLAlchemy and multiprocessing的后续内容。正如在这个问题中讨论的,pickle异常在Python中是有问题的。这通常不是问题,但有一种情况是,python多处理模块中发生错误。由于多处理通过酸洗来移动对象,如果在多处理进程中发生错误,整个进程可能会挂起,如问题所示。在
一种可能的方法是修复所有有问题的异常,正如在该问题中所讨论的那样。这不是一件容易的事,因为我们不可能轻易地提前知道哪些异常可以被调用。另一种方法是suggested by lbolla in an answer to the question,它是捕捉异常,构造一个等效的无害异常,然后重新抛出。 但是,我不知道该怎么做。考虑下面的代码。在
class BadExc(Exception):
def __init__(self, message, a):
'''Non-optional param in the constructor.'''
Exception.__init__(self, message)
self.a = a
import sys
try:
try:
#print foo
raise BadExc("bad exception error message", "a")
except Exception, e:
raise Exception(e.__class__.__name__ + ": " +str(e)), None, sys.exc_info()[2]
except Exception, f:
pass
import cPickle
a = cPickle.dumps(f)
l = cPickle.loads(a)
print "raising error"
raise sys.exc_info()[0], sys.exc_info()[1], sys.exc_info()[2]
这段代码对异常进行pickle和unpickle,然后抛出它,给出错误
^{pr2}$学分到Glenn Maynard's answer to "“Inner exception” (with traceback) in Python?"。 这有重要的东西,即回溯、错误消息和异常类型,所以这可能是最好的方法。但理想的情况下,我想要一个和最初的例外完全一样的东西,即
Traceback (most recent call last):
File "<stdin>", line 11, in <module>
__main__.BadExc: bad exception error message
或者更一般地说,在前面加上异常的名称,而不是Exception
。这可能吗?在
或者,可以使用print foo
语句代替BadExc
类,它给出一个NameError
。但是,此异常不需要特殊处理。在
您可以重写^{} 以获得所需的结果。它至少在这个例子中有效,但它相当粗糙,所以请测试,不要承诺:-)
(编辑:我对此不太满意,因为现在有两个参数的“正常”异常也会得到不同的处理。可能的解决方案是通过传递“PICKLED”作为第一个参数,然后检查它,而不是检查
args
的长度,从而“标记”您的特殊异常。)然后用两个参数创建
^{pr2}$Exception
,即名称(__module__.__class__
)和Exception
消息(str(e)
):那么这个:
印刷品:
相关问题 更多 >
编程相关推荐