ValueError: 'a' cannot be empty unless no samples are taken

Here, I met the error message as follows:

def maldroid_noniid(dataset, train_labels, num_users):
    num_shards, num_imgs = 110, 120
    idx_shard = [i for i in range(num_shards)]
    dict_users = {i: np.array([]) for i in range(num_users)}
    idxs = np.arange(num_shards*num_imgs)
    labels = torch.Tensor(train_labels)

    # sort labels
    idxs_labels = np.vstack((idxs, labels))
    idxs_labels = idxs_labels[:, idxs_labels[1, :].argsort()]
    idxs = idxs_labels[0, :]

    # divide and assign
    for i in range(num_users):
        rand_set = set(np.random.choice(idx_shard, 2, replace=False))
        idx_shard = list(set(idx_shard) - rand_set)
        for rand in rand_set:
            dict_users[i] = np.concatenate(
                (dict_users[i], idxs[rand*num_imgs:(rand+1)*num_imgs]), axis=0)

    return dict_users

When I compile the above Python code,

File "mtrand.pyx", line 909, in numpy.random.mtrand.RandomState.choice from np.random.choice
ValueError: 'a' cannot be empty unless no samples are taken

This error message was output.

The above Python code is non-i.i.d. This is the code to configure the dataset of Does anyone know why this error message pops up and how to fix this problem?

The error in the code is caused since idx_shard is an empty list when the following code is run-

np.random.choice(idx_shard, 2, replace=False)

Since you use np.random.choice with size=2 and replace=False, the size of the input must be at least 2.

The error you get occurs when the size of the input is 0.

This can be solved in multiple ways in your case. Possible solutions-

  • Inside the for loop for i in range(num_users): - check if index_shared is empty, and if it is, break
  • Add an assert in the start of the function to make sure that num_users <= num_shards / 2

Any other solution which prevents chosing from idx_shard when it is empty (or has one item) will work :)

posted @ 2024-05-12 16:21  咖啡陪你  阅读(228)  评论(0编辑  收藏  举报