【发布时间】:2016-08-13 16:25:24
【问题描述】:
我正在尝试将现有类(不是我创建的)的所有方法包装到 try/except 套件中。它可以是任何类,但我将在此处使用 pandas.DataFrame 类作为实际示例。
所以如果调用的方法成功了,我们就继续前进。但是如果它应该生成一个异常,它会被附加到一个列表中以供以后检查/发现(尽管为了简单起见,下面的示例只是发出一个打印语句)。
(请注意,调用实例上的方法时可能发生的与数据相关的异常类型尚不清楚;这就是本练习的原因:发现)。
这个post 非常有帮助(尤其是@martineau Python-3 的答案),但我无法适应它。下面,我预计对(包装的)info() 方法的第二次调用会发出打印输出,但遗憾的是,它没有。
#!/usr/bin/env python3
import functools, types, pandas
def method_wrapper(method):
@functools.wraps(method)
def wrapper(*args, **kwargs): #Note: args[0] points to 'self'.
try:
print('Calling: {}.{}()... '.format(args[0].__class__.__name__,
method.__name__))
return method(*args, **kwargs)
except Exception:
print('Exception: %r' % sys.exc_info()) # Something trivial.
#<Actual code would append that exception info to a list>.
return wrapper
class MetaClass(type):
def __new__(mcs, class_name, base_classes, classDict):
newClassDict = {}
for attributeName, attribute in classDict.items():
if type(attribute) == types.FunctionType: # Replace it with a
attribute = method_wrapper(attribute) # decorated version.
newClassDict[attributeName] = attribute
return type.__new__(mcs, class_name, base_classes, newClassDict)
class WrappedDataFrame2(MetaClass('WrappedDataFrame',
(pandas.DataFrame, object,), {}),
metaclass=type):
pass
print('Unwrapped pandas.DataFrame().info():')
pandas.DataFrame().info()
print('\n\nWrapped pandas.DataFrame().info():')
WrappedDataFrame2().info()
print()
这个输出:
Unwrapped pandas.DataFrame().info():
<class 'pandas.core.frame.DataFrame'>
Index: 0 entries
Empty DataFrame
Wrapped pandas.DataFrame().info(): <-- Missing print statement after this line.
<class '__main__.WrappedDataFrame2'>
Index: 0 entries
Empty WrappedDataFrame2
总之,...
>>> unwrapped_object.someMethod(...)
# Should be mirrored by ...
>>> wrapping_object.someMethod(...)
# Including signature, docstring, etc. (i.e. all attributes); except that it
# executes inside a try/except suite (so I can catch exceptions generically).
【问题讨论】:
-
P.S.如果我延迟回复 cmets 或 answer,可能是因为我正在尝试建议或尝试先理解它。 =:)
标签: python-3.x metaprogramming wrapper metaclass python-decorators