我在调用__new__
方法时遇到了困难。
创建A()的实例时,如果输入低于10,我想返回B()
的实例。但实例是在不运行__new__
或{{1}的情况下创建的* } __init__
的方法,为什么会这样?
B
此输出
class A (object):
def __init__ (self, IP, s):
print 'arrived to init a'
self.IP=IP
print self.IP
print s
def __new__ (cls, IP, s):
print "arrived to new a"
if IP>10:
self = object.__new__ (cls)
return self # return n
else:
return super (cls, A).__new__ (B)
class B(object):
def __init__(self,d,s,ar):
print 'arrived to b'
self.ip=d
print self.ip
print s
print ar
def __new__(cls,d,s,ar):
print 'arrived to new b'
self = object.__new__(cls)
return self # return n
def __repr__(self):
return 'B({}, ..., ...)'.format(getattr(self, 'ip', '<missing>'))
a = A(10 ,"a")
print a
而不是
arrived to new a
B(<missing>, ..., ...)
答案 0 :(得分:1)
您要求object.__new__
在此处创建新实例:
return super (cls, A).__new__ (B)
所以A.__new__
在这里返回B()
的实例,而因为这会返回一个新的B()
实例,而不是新的A()
实例,B.__init__()
永远不会被召唤;类型需要匹配。请参阅object.__new__
documentation:
如果
__new__()
返回cls
的实例,则会调用新实例的__init__()
方法,如__init__(self[, ...])
,其中self
是新实例,其余参数与传递给__new__()
的参数相同。
B()
不是A
的实例,因此不会调用__init__
。 B.__new__
未被调用,因为您通过要求object.__new__
代替创建实例来明确绕过它。
只需在B()
中直接致电A.__new__
:
if IP>10:
self = object.__new__ (cls)
return self # return n
else:
return B(IP, s, 42)
你需要传入三个参数;我为第三个人制作了42
。
由于调用了B()
,因此将调用B.__new__
。由于B.__new__
会返回B
的实例,因此也会调用__init__
方法。
演示:
>>> A(10 ,"a")
arrived to new a
arrived to new b
arrived to b
10
a
42
B(10, ..., ...)