编程珠玑笔记之取样问题
时间:2010-11-08 来源:小培
解决方法1:找一个随机数,在没有被筛选出来的数字里面求模,然后输出。当还剩5个数字时,每个元素的概率为20%,选出一个,每个元素的概率为25%。这样对于选出的每个元素来说,都是平等的。
void genkunth(int m,int n)
{
for(int i=0;i<n;i++)
{
/*selectm of remaining n-i*/
if((bigrand()%(n-i))<m)//
{
count << i << "\n";
m--;
}
}
}
解决方法2:在一个初始为空的集合里面插入随机整数,直到个数足够。然后按照顺序输出。
void gensets(int m,int n)
{
set<int> S;
while(S.size()<m)
s.insert(bigrand()%n);
set<int>::iteratori;
for(i=S.begin();i!=S.end();++i)
count<< *i << "\n";
}
解决方法3: 把0~n-1的数组顺序打乱,然后把前m个元素输出。其实只需要打乱数组的前m个元素就可以。
void genshuf(int m,int n)
{
int i,j;
int *x = new int[n];
for(i=0;i<n;i++)
x[i]=i;
for(i=0;i<m;i++)
{
j= randint(i,n-1);
int t =x[i]; x[i] = x[j];x[j]=t;
}
sort(x,x+m);
for(i=0;i<m;i++)
count<<x[i]<<"\n";
}
特殊情况:
如果n为100万而m为n-10时, 生成一个包含10个元素的有序随机样本,然后输出不在样本中的整数。
如果m为1000万而n为2的31次方,先生成1100万个整数,然后排序并对其扫描以删除重复的元素,最后得到一个有1000万元素的有序样本。(这一条不太理解,思考中)