首页
学习
活动
专区
圈层
工具
发布
社区首页 >问答首页 >容器的Itertools

容器的Itertools
EN

Stack Overflow用户
提问于 2011-08-15 06:42:58
回答 3查看 375关注 0票数 9

考虑以下交互式示例

代码语言:javascript
复制
>>> l=imap(str,xrange(1,4))
>>> list(l)
['1', '2', '3']
>>> list(l)
[]

有没有人知道在某个地方已经有一个imap版本的实现(和其他itertools函数),这样第二个time list(l)就会被执行,你会得到和第一个一样的结果。我不想要常规的map,因为如果您使用更大的范围,在内存中构建整个输出可能是对内存的浪费。

我想要的东西基本上是这样的

代码语言:javascript
复制
class cmap:
    def __init__(self, function, *iterators):
        self._function = function
        self._iterators = iterators

    def __iter__(self):
        return itertools.imap(self._function, *self._iterators)

    def __len__(self):
        return min( map(len, self._iterators) )

但是,如果有人已经这样做了,那么为所有itertools手动执行此操作将是浪费时间。

ps。您是否认为容器比迭代器更具禅意,因为对于迭代器来说,

代码语言:javascript
复制
for i in iterator:
    do something

隐式清空迭代器,而容器需要显式删除元素。

EN

回答 3

Stack Overflow用户

回答已采纳

发布于 2011-08-15 06:52:51

您不必为每种类型的容器构建这样的对象。基本上,您拥有以下内容:

代码语言:javascript
复制
mkimap = lambda: imap(str,xrange(1,4))
list(mkimap())
list(mkimap())

现在你只需要一个很好的包装对象来防止“丑陋”的函数调用。这可能是这样的:

代码语言:javascript
复制
class MultiIter(object):
    def __init__(self, f, *a, **k):
        if a or k:
            self.create = lambda: f(*a, **k)
        else: # optimize
            self.create = f
    def __iter__(self):
        return self.create()

l = MultiIter(lambda: imap(str, xrange(1,4)))
# or
l = MultiIter(imap, str, xrange(1,4))
# or even
@MultiIter
def l():
    return imap(str, xrange(1,4))

# and then
print list(l)
print list(l)

(未经测试,希望它能工作,但你应该明白这个想法)

关于你的第二个问题:迭代器和容器都有它们的用途。你应该选择最适合你需要的东西。

票数 7
EN

Stack Overflow用户

发布于 2011-08-15 06:52:05

您可能正在寻找itertools.tee()

票数 1
EN

Stack Overflow用户

发布于 2011-08-15 09:17:23

迭代器是我最喜欢的话题;)

代码语言:javascript
复制
from itertools import imap

class imap2(object):
    def __init__(self, f, *args):
        self.g = imap(f,*args)
        self.lst = []
        self.done = False

    def __iter__(self):
        while True:
            try: # try to get something from g
                x = next(self.g)
            except StopIteration:
                if self.done:
                    # give the old values
                    for x in self.lst:
                        yield x
                else:
                    # g was consumed for the first time
                    self.done = True
                return
            else:
                self.lst.append(x)
                yield x




l=imap2(str,xrange(1,4))
print list(l)
print list(l)
票数 -1
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/7060229

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档