考虑假设函数repeatcall
,它将no-args可调用func
和正整数n
作为参数,并返回一个列表,其成员是通过执行{{1}获得的} func()
次。它支持无限的愚蠢的hijinks流,如:
n
我可以发誓我在Python 2.x标准库中看到了>>> repeatcall(lambda: id(dict()), 5)
[45789920, 45788064, 45807216, 45634816, 45798640]
>>> urandom = lambda: struct.unpack('Q', open('/dev/urandom').read(8))[0]
>>> repeatcall(urandom, 3)
[3199039843823449742, 14990726001693341311L, 11583468019313082272L]
>>> class Counter(itertools.count): __call__ = itertools.count.next
>>> repeatcall(Counter(100, -2), 4)
[100, 98, 96, 94]
之类的函数,但我找不到它。如果我没有想到这一点,我可以找到标准库中的 吗?
PS:我知道推出自己的产品是微不足道的,但我讨厌重新发明轮子,尤其是那些已经在标准库中的轮子。我不询问如何自己动手。
编辑:让更明确,我不会问如何编码repeatcall
。
答案 0 :(得分:13)
您已在标准库文档中看到过这种情况,而不是标准库本身。
的repeatfunc
def repeatfunc(func, times=None, *args):
"""Repeat calls to func with specified arguments.
Example: repeatfunc(random.random)
"""
if times is None:
return starmap(func, repeat(args))
return starmap(func, repeat(args, times))
它允许参数并且(理论上)应该比列表理解更好地执行,因为func
只需要查找一次。当你没有真正使用计数器时,repeat
也比range
快。
答案 1 :(得分:3)
你的意思是这样的吗?:
>> from random import random
>> print [random() for x in range(5)]
[0.015015074309405185,
0.7877023608913573,
0.2940706206824023,
0.7140457069245207,
0.07868376815555878]
似乎足够简洁吗?
答案 2 :(得分:3)
这是不存在的原因:对每个调用不带参数的函数进行编码的惯用方法,以及返回新内容的方法是将其编码为生成器。
然后,您可以使用列表推导或生成器表达式多次调用它:[next(gen) for i in xrange(5)]
。更好的是,gen
本身可以是(id(dict()) for i in (itertools.repeat(None)))
等生成器表达式的结果。
因此, python没有库支持,因为它在语法上支持它。
答案 3 :(得分:2)
您可以使用apply内置功能
>>> def repeatcall(func,n):
[apply(func) for i in range(0,n)]
>>> repeatcall(lambda: id(dict()), 5)
[56422096, 56422240, 56447024, 56447168, 56447312]
>>> import itertools
>>> class Counter(itertools.count): __call__ = itertools.count.next
>>> repeatcall(Counter(100, -2), 4)
[100, 98, 96, 94]
>>>
注意** 从手册 apply()的使用等同于函数(* args,** keywords)。
所以repeatcall也可以写成
>>> def repeatcall(func,n):
[func() for i in range(0,n)]