iter迭代无线循环错误
我在阅读werkzeug中实现的flask Header
类的时候,碰到了这个装饰器。
def native_itermethods(names):
def setmethod(cls, name):
itermethod = getattr(cls, name)
setattr(cls, 'iter%s' % name, itermethod)
listmethod = lambda self, *a, **kw: list(itermethod(self, *a, **kw))
listmethod.__doc__ = \
'Like:py:meth:`iter%s`, but returns a list.' % name
setattr(cls, name, listmethod)
def wrap(cls):
for name in names:
setmethod(cls, name)
return cls
return wrap
这部分代码会对该类下创建一个iter
开头的方法。比如get
会创建出一个iterget
。并把原来的get
的返回值改为迭代iterget
的列表。这是我理解的如果有错误请指正。
我想要对上边的装饰器进行测试验证以下是我的代码
iterget = lambda d, *arg, **kw: d.iterget(*arg, **kw)
@native_itermethods(['get'])
class A(object):
def __init__(self):
self._names = [('mink', '123'), ('kk', '1211')]
def __iter__(self):
yield iter(self._names)
def get(self, name):
for key, value in iterget(self):
if key == name:
yield key, value
if __name__ == '__main__':
a = A()
print dir(a)
print a.get('mink')
按照我的理解上面装饰器的结果应该返回一个元组列表,但是会爆出以下错误
是我例子写错了么还是,我对上述代码没有理解对。
如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。
绑定邮箱获取回复消息
由于您还没有绑定你的真实邮箱,如果其他用户或者作者回复了您的评论,将不能在第一时间通知您!
发布评论
评论(1)
首先是这个不是无限循环,而是递归超过了栈深度。
在 native_itermethods 里面,会把外面的A.get放在作为A对象iterget方法,并且用list(A.iterget)覆盖原来的A.get。在你的A.get定义里面,由于A.get已经调用了A.iterget,这其实就会是自身调用自身,会无限的递归下去,从而导致栈溢出错误。
这个函数的目的主要是方便把对象里原来的迭代器方法的名字变成itername,然后让原来的名字返回一个list后的结果。