__repr__ 中的函数导致无限递归
Function inside __repr__ results in infinite recursion
我正在学习 Python,我尝试编写以下代码。
class AttributeDisplay:
'''Display all attributes of a class in __repr__.
It can be inherited.'''
def gatherAttributes(self):
'''Gather all attributes and concatenate them
as a string'''
def getAttributeNameAndValue(key):
return '[%s] - [%s]' % (key, getattr(self, key))
return '\n'.join((map(getAttributeNameAndValue, sorted(self.__dict__))))
def __repr__(self):
'''Print all attributes'''
attr = self.gatherAttributes() # omitting () results in infinite recursion
return '[Class: %s]\n%s' % (self.__class__.__name__, attr)
我不小心漏掉了括号,attr 变成了函数而不是字符串。但是,当我调用print(X)
时,它进入了无限递归。
错误代码如下
def __repr__(self):
'''Print all attributes'''
attr = self.gatherAttributes # omitting () results in infinite recursion
return '[Class: %s]\n%s' % (self.__class__.__name__, attr)
File "Some Folder/classtools.py", line 18, in __repr__
return '[Class: %s]\n%s' % (self.__class__.__name__, attr)
[Previous line repeated 244 more times]
RecursionError: maximum recursion depth exceeded while calling a Python object
我尝试调试但找不到此行为的确切原因。即使我不小心留下了括号,它也应该打印 <function object ...>
对吗?
为什么在__repr__
这种情况下调用自己?
提前致谢。
编辑:测试代码如下
if __name__ == '__main__':
class TopTest(AttributeDisplay):
count = 0
def __init__(self):
self.attr1 = TopTest.count
self.attr2 = TopTest.count+1
TopTest.count += 2
class SubTest(TopTest):
pass
def test():
t1, t2 = TopTest(), SubTest()
print(t1)
print(t2)
test()
这是因为绑定方法的repr
包含了它绑定的对象:
>>> class C:
... def __repr__(self):
... return '<repr here!>'
... def x(self): pass
...
>>> C().x
<bound method C.x of <repr here!>>
>>> str(C().x)
'<bound method C.x of <repr here!>>'
请注意,我在这里做了一些飞跃 -- 它们是:
'%s' % x
大致相当于 str(x)
- 当某些东西没有定义
__str__
时,它会退回到 __repr__
(方法描述符就是这种情况)
在检索 class 的 repr 时,你会得到这个循环:
AttributeDisplay.__repr__
=>
AttributeDisplay.gatherAttributes.__repr__
=>
AttributeDisplay.__repr__
(class 的 repr 作为绑定方法 repr 的一部分)=>
- ...
我正在学习 Python,我尝试编写以下代码。
class AttributeDisplay:
'''Display all attributes of a class in __repr__.
It can be inherited.'''
def gatherAttributes(self):
'''Gather all attributes and concatenate them
as a string'''
def getAttributeNameAndValue(key):
return '[%s] - [%s]' % (key, getattr(self, key))
return '\n'.join((map(getAttributeNameAndValue, sorted(self.__dict__))))
def __repr__(self):
'''Print all attributes'''
attr = self.gatherAttributes() # omitting () results in infinite recursion
return '[Class: %s]\n%s' % (self.__class__.__name__, attr)
我不小心漏掉了括号,attr 变成了函数而不是字符串。但是,当我调用print(X)
时,它进入了无限递归。
错误代码如下
def __repr__(self):
'''Print all attributes'''
attr = self.gatherAttributes # omitting () results in infinite recursion
return '[Class: %s]\n%s' % (self.__class__.__name__, attr)
File "Some Folder/classtools.py", line 18, in __repr__
return '[Class: %s]\n%s' % (self.__class__.__name__, attr)
[Previous line repeated 244 more times]
RecursionError: maximum recursion depth exceeded while calling a Python object
我尝试调试但找不到此行为的确切原因。即使我不小心留下了括号,它也应该打印 <function object ...>
对吗?
为什么在__repr__
这种情况下调用自己?
提前致谢。
编辑:测试代码如下
if __name__ == '__main__':
class TopTest(AttributeDisplay):
count = 0
def __init__(self):
self.attr1 = TopTest.count
self.attr2 = TopTest.count+1
TopTest.count += 2
class SubTest(TopTest):
pass
def test():
t1, t2 = TopTest(), SubTest()
print(t1)
print(t2)
test()
这是因为绑定方法的repr
包含了它绑定的对象:
>>> class C:
... def __repr__(self):
... return '<repr here!>'
... def x(self): pass
...
>>> C().x
<bound method C.x of <repr here!>>
>>> str(C().x)
'<bound method C.x of <repr here!>>'
请注意,我在这里做了一些飞跃 -- 它们是:
'%s' % x
大致相当于str(x)
- 当某些东西没有定义
__str__
时,它会退回到__repr__
(方法描述符就是这种情况)
在检索 class 的 repr 时,你会得到这个循环:
AttributeDisplay.__repr__
=>AttributeDisplay.gatherAttributes.__repr__
=>AttributeDisplay.__repr__
(class 的 repr 作为绑定方法 repr 的一部分)=>- ...