从集合中获取X个唯一数字

时间:2010-07-10 03:10:18

标签: algorithm random theory set unique

抓住独特随机数的最优雅方法是什么?

目前我需要随机的唯一数字,我通过使用while循环检查它是否不唯一,看看我之前是否使用过随机数。

所以它看起来像:

int n = getRandomNumber % [Array Size];

for each ( Previously used n in list)
    Check if I've used n before, if I have...try again.

有许多方法可以解决这个线性O(n / 2)问题,我只是想知道是否有一种优雅的方法来解决它。试着回想MATH115离散数学并记住这位老讲师是否涵盖了与看似微不足道的问题有关的事情。

我现在想不到,所以也许一旦我喝了一些咖啡因,我的大脑就会用咖啡引起的智商提高来吸引它。

4 个答案:

答案 0 :(得分:5)

如果你想要从集合{1,...,n}中无需替换(获得唯一数字)的k个随机整数,你想要的是[n]随机排列中的前k个元素。生成这种随机排列的最优雅方法是使用Knuth shuffle。见这里:http://en.wikipedia.org/wiki/Knuth_shuffle

答案 1 :(得分:3)

  

抓住我想到的独特随机数?

  1. 创建N个唯一元素的数组(例如,范围为0..N-1的整数),将N存储为arraySize和initialArraySize(arraySize = N; initialArraySize = N)
  2. 请求随机数时:
    2.1如果arraySize为零,则arraySize = initialArraySize
    2.1生成index = getRandomNuber()%arraySize
    2.3 result = array [index]。不要返回结果。
    2.2交换数组[index]与数组[arraySize-1]。交换意味着“交换”c =数组[index]; array [index] = array [arraySize-1]; array [arraySize-1] = c
    2.3将arraySize减少1.
    2.4返回结果。
  3. 您将获得一个随机数列表,在您用完唯一值之前,这些列表不会重复。 O(1)复杂性。

答案 2 :(得分:1)

n位最大周期线性移位反馈寄存器(LFSR)将在内部状态重复之前循环通过其所有(2 ^ n -1)个内部状态。当且仅当由抽头序列加1形成的多项式是原始多项式mod 2时,LFSR才是最大周期LFSR。

因此,n位最大周期LFSR将为您提供一系列(2 ^ n - 1)个唯一随机数,每个随机数为n位长。

LFSR非常优雅。

答案 3 :(得分:0)

由于您要强加唯一性,因此伪随机生成器应该足够,可以将其配置为不重复您可能需要的序列。例如,LCG:如果种子是uint32且最初为0,则使用(1664525 *种子)+ 1013904223作为下一个种子,并将低位字作为未重复的16位结果。