最簡單的方法是在下面的cyclezip1
。它對於大多數目的來說足夠快。
import itertools
def cyclezip1(it1, it2, count):
pairs = itertools.izip(itertools.cycle(iter1),
itertools.cycle(iter2))
return itertools.islice(pairs, 0, count)
這裏是它的另一個實現,大約快兩倍,當count
大於it1
和it2
最小公倍數顯著較大。
import fractions
def cyclezip2(co1, co2, count):
l1 = len(co1)
l2 = len(co2)
lcm = l1 * l2/float(fractions.gcd(l1, l2))
pairs = itertools.izip(itertools.cycle(co1),
itertools.cycle(co2))
pairs = itertools.islice(pairs, 0, lcm)
pairs = itertools.cycle(pairs)
return itertools.islice(pairs, 0, count)
在這裏,我們採取的事實,即對將他們的第一n
其中n
是len(it1)
和len(it2)
最不常見的複式後周期。這當然假定iterables是集合,因此要求它們的長度是有意義的。可以做了進一步的優化是 更換線
pairs = itertools.islice(pairs, 0, lcm)
與
pairs = list(itertools.islice(pairs, 0, lcm))
這是幾乎沒有顯着的改善(在我的測試約2%),幾乎沒有一致。它也需要更多的內存。如果預先知道it1
和it2
要足夠小,以便額外的內存可以忽略不計,那麼可以從中擠出額外的性能。
有趣的是,在收集的情況下,顯而易見的事情比第一個選項慢四倍。
def cyclezip3(co1, co2, count):
l1 = len(co1)
l2 = len(co2)
return ((co1[i%l1], co2[i%l2]) for i in xrange(count))
簡單勝利! – cwall 2010-09-24 17:23:38