受此早期堆栈溢出问题的启发,我一直在考虑如何在python中随机交错迭代,同时保留每个迭代中元素的顺序.例如:
>>> def interleave(*iterables):
... "Return the source iterables randomly interleaved"
... <insert magic here>
>>> interleave(xrange(1, 5), xrange(5, 10), xrange(10, 15))
[1, 5, 10, 11, 2, 6, 3, 12, 4, 13, 7, 14, 8, 9]
Run Code Online (Sandbox Code Playgroud)
原始问题要求随机交错两个列表a和b,并且接受的解决方案是:
>>> c = [x.pop(0) for x in random.sample([a]*len(a) + [b]*len(b), len(a)+len(b))]
Run Code Online (Sandbox Code Playgroud)
然而,这种解决方案适用于只有两个列表(尽管它可以很容易地扩展),并依赖于一个事实,即a和b是列表,以便pop()和len()可以叫上他们,这意味着它不能与iterables使用.它还有清空源列表a和b的不幸副作用.
给出原始问题的替代答案会获取源列表的副本以避免修改它们,但这对我来说效率低下,特别是如果源列表相当大.备用答案也可以使用,len()因此不能仅用于迭代.
我编写了自己的解决方案,适用于任意数量的输入列表,不会修改它们:
def interleave(*args):
iters = [i for i, b in ((iter(a), a) for a in args) for _ in xrange(len(b))]
random.shuffle(iters)
return …Run Code Online (Sandbox Code Playgroud) python ×1