如果我有这门课程:
class MyClass(object):
pass
然后我这样做:
instance = MyClass()
instance.new_method()
我遇到了一个AttributeError Exception,但是我想以dinamically方式创建这个方法并返回一个especifc值。有可能吗?
答案 0 :(得分:2)
首先,Python检查是否存在具有此类名称的属性,如果是,则会调用它。没有明确的方法可以过早地检测是否会调用此属性。
这是实现目标的棘手方法:
class Dispatcher(object):
def __init__(self, caller, name):
self.name = name
self.caller = caller
def __call__(self, *a, **ka):
print('Call on Dispatcher registered!',
'Will create method on',
self.caller.__class__.__name__,
'now.')
setattr(self.caller, self.name, self.mock)
return getattr(self.caller, self.name)(*a, **ka)
@classmethod
def mock(cls, *a, **ka):
return 'Some default value for newly created methods.'
class MyClass(object):
def __getattr__(self, attr):
return Dispatcher(self, attr)
instance = MyClass()
print(instance.new_method, '\n')
print(instance.new_method(), '\n')
print(instance.new_method(), '\n')
print(instance.other_method)
输出:
<__main__.Dispatcher object at 0x0000000002C07DD8>
Call on Dispatcher registered! Will create method on MyClass now.
Some default value for newly created methods.
Some default value for newly created methods.
<__main__.Dispatcher object at 0x0000000002C07DD8>
虽然此解决方案非常全面,但每次尝试访问不存在的属性时,它都会返回Dispatcher
的新实例。
如果调用Dispatcher
实例(例如Dispatcher(self, attr)()
),它会将mock
设置为对象的名为attr
的新方法,作为第一个参数传递给构造
答案 1 :(得分:1)
是的,你可以这样做:
class MyClass(object):
pass
def some_method():
pass
name = 'new_method'
setattr(MyClass, name, classmethod(some_method))
答案 2 :(得分:1)
有可能。
>>> class MyClass(object):
pass
>>> instance = MyClass()
>>> def new_method(cls, x):
print x
>>> MyClass.new_method = new_method
>>> instance.new_method(45)
45
请注意,new_method
有cls
作为第一个参数(实例)在作为实例方法调用时被隐式传递。