我想从两个列表的产品中获取 n 样本(无需替换)。如下所示,我目前正在计算整个产品,然后从中进行采样,但这对于长列表而言在计算上是不实用的。有没有办法优化这个过程?也就是说,不必计算整个产品,而是更有效地采样?
当前天真的方法(如下所述,错误地替换替换):
from itertools import product
from random import choice
def get_sample(a,b,n):
"""return n samples from the product a and b"""
D = list(product(a,b))
D = [choice(D) for _ in range(n)]
return D
答案 0 :(得分:1)
如果你实际上使用list
,如果你想要 list
,你应该没事。
from itertools import product
def get_first_n_sample(a,b,n):
"""return n samples from the product a and b"""
D = product(a,b)
D = [D.next() for _ in range(n)] ## if you're on Python2, use xrange!
return D
现在,如果您只想要来自a
和b
的某些组合的随机样本,则迭代器显然不是正确的方法,因此,itertools
也不是。假设a
和b
随机访问速度很快(例如list
s,tuple
s):
from random import choice
def get_random_sample(a, b):
return (choice(a), choice(b))
获取n
唯一的样本会更复杂,但是:
from random import sample
def get_random_samples(a, b, n):
n_prod = len(a) * len(b)
indices = sample(range(n_prod), n)
return [(a[idx % len(a)], b[idx // len(a)]) for idx in indices]
答案 1 :(得分:0)
如果您想要一个替换样本,代码目前的方式,您可以使用product(a, b)
随机添加(choice(a), choice(b)
元素:
sample = [(choice(a), choice(b)) for _ in xrange(n)]
如果您想要一个没有替换的样本,请制作一组随机索引的样本:
sample = [(a[i // len(b)], b[i % len(b)])
for i in random.sample(xrange(len(a)*len(b)), n)]
答案 2 :(得分:-1)
不幸的是,您无法从迭代器中获取随机样本。迭代器(如product
)表示您一次只知道1个值,并且您必须知道多于1个值才能提供随机性。
使用random.sample()
这样的天真方法可以更有效:
from itertools import product
import random
def get_sample(a,b,n):
"""return n samples from the product a and b"""
D = list(product(a,b))
return random.sample(D, n)