产生不同的随机数,转化一下更类似于随机取样的问题,从N个不重复的数中,取出m个数。
1、使用java的Set集合,Set保证新增的元素不能与集合中已有的元素重复;LinkedHashSet、TreeSet都能实现,后者集合里的元素按升序排列;
2、用数组保存N个值,然后打乱数组,取前m个数;
3、Knuth算法,主要思想是从r个剩余的整数中选出s个,以概率s/r选择下一个数, rand()%remaining<select,当条件符合时,select自减1,而remaining是不断减小的。
当remaining==select时,不等式必然成立,肯定会选择一个数;而当select变为0时,等式必然不成立;所以一定会选出select个数,而且是递增有序的
/**
* 总结几种产生不同随机数的方法
* 1、使用Java的Set集合来产生,无序LinkedHashSet,有序TreeSet
* 2、数组交换
* 3、bigrand()%remain<select来选择,
*/
package codeant.random;
import java.util.LinkedHashSet;
import java.util.Random;
import java.util.TreeSet;
public class DiffRandom {
public static void Swap(int []a,int i,int j)
{
int temp=a[i];a[i]=a[j];a[j]=temp;
}
public static void main(String []args){
Random random=new Random(System.currentTimeMillis());
int maxNumber=6;
System.out.println("测试,产生"+maxNumber+"个不同随机数1~10");
//LinkdedHashSet
LinkedHashSet<Integer> linkedHashSet=new LinkedHashSet<Integer>();
System.out.print("LinkedHashSet:");
while(linkedHashSet.size()<6)
linkedHashSet.add(random.nextInt(10));
System.out.println(linkedHashSet);
//TreeSet排序的无重复随机数
System.out.print("TreeSet:");
TreeSet<Integer> treeSet=new TreeSet<Integer>();
while(treeSet.size()<6)
treeSet.add(random.nextInt(10));
System.out.println(treeSet);
//交换数组的方法,首先初始化
int []array=new int [10];
for(int i=0;i<10;i++)
array[i]=i;
for(int i=0;i<5;i++)
Swap(array, i, random.nextInt(10-i-1));
System.out.print("Array:");
for(int i=0;i<6;i++)
System.out.print(array[i]+" ");
//Knuth算法
System.out.print("\nbigrand()%remain<select:");
for(int i=0;i<10;i++)
{
if(random.nextInt()%(10-i)<maxNumber)
{
array[maxNumber]=i;
System.out.print(array[maxNumber]+" ");
maxNumber--;
}
}
}
}