Образец из раздела равномерно в Python - PullRequest
0 голосов
/ 29 февраля 2020

Я бы хотел сделать выборку из раздела n = 500, k = 12. Я знаю, что это абсурдно большое число.

Я использую more_itertools., чтобы получить список разделов.

ex для n = 5, k = 3

>>>>from more_itertools import set_partitions

>>>>list(set_partitions(range(5), 3))
Out[2]: 
[[[0], [1], [2, 3, 4]],
 [[0], [1, 2], [3, 4]],
 [[0], [2], [1, 3, 4]],
 [[0], [1, 2, 3], [4]],
 [[0], [2, 3], [1, 4]],
 [[0], [1, 3], [2, 4]],
 [[0], [3], [1, 2, 4]],
 [[0, 1], [2], [3, 4]],
 [[1], [0, 2], [3, 4]],
 [[1], [2], [0, 3, 4]],
 [[0, 1], [2, 3], [4]],
 [[1], [0, 2, 3], [4]],
 [[1], [2, 3], [0, 4]],
 [[0, 1], [3], [2, 4]],
 [[1], [0, 3], [2, 4]],
 [[1], [3], [0, 2, 4]],
 [[0, 1, 2], [3], [4]],
 [[1, 2], [0, 3], [4]],
 [[1, 2], [3], [0, 4]],
 [[0, 2], [1, 3], [4]],
 [[2], [0, 1, 3], [4]],
 [[2], [1, 3], [0, 4]],
 [[0, 2], [3], [1, 4]],
 [[2], [0, 3], [1, 4]],
 [[2], [3], [0, 1, 4]]]

Проблема в том, что для n = 500 и k = 12 это безумно велико! Он все равно будет работать, поскольку он является генератором и, следовательно, ничего не хранит в памяти, однако порядок не случайный.

Я изначально думал о случайном назначении 500 элементов на 12 наборов, используя следующий код -

n=500; k=12; ele_arr = list(range(n)); np.random.shuffle(ele_arr);

output = [[] for i in range(k)]
for i, e in enumerate(ele_arr):
    # have to ensure that each partition has at least one element
    if i < k:
        output[i].append(e)
    else:
        j = np.random.randint(0, k-1)
        output[j].append(e)

Но я не уверен, что это приведет к единой случайной выборке всех возможных разделов.

...