我无法让rand()在C ++中工作。 rand()通常给我一个非常大的数字。当我尝试使用模运算符(%)给它一个范围时,它总是返回0,无论如何。
在程序开头播种随机数生成器也无济于事。
答案 0 :(得分:8)
我认为如果随机生成器算法将某个位模式保留为零,这种情况很常见。 (例如,如果低位为零,则某个低常量的数字mod将始终为零。)
也许你应该尝试类似的东西:
const int desired_maximum = /* ... */;
int r = (((double)rand()) / RAND_MAX) * desired_maximum;
例如在this manpage link中,它说:
C中的数字食谱:科学计算的艺术(William H. Press,Brian P. Flannery,Saul A. Teukolsky,William T. Vetterling; New York:Cambridge University Press,1992(2nd ed。,p。 277)),提出以下意见:
“如果要生成1到10之间的随机整数,则应始终使用高位来执行此操作,如
从来没有任何类似的东西j = 1 + (int) (10.0 * (rand() / (RAND_MAX + 1.0)));(使用低阶位)。“j = 1 + (rand() % 10);
答案 1 :(得分:7)
以下代码对我来说效果很好(每次运行时发出0到0和1000之间的随机数):
#include <cstdlib>
#include <ctime>
#include <iostream>
int main()
{
std::srand(time(0));
std::cout<<(std::rand() % 1000)<<std::endl;
return 0;
}
答案 2 :(得分:4)
看来您的问题已经得到解决,但我认为还值得一提。使用余数将rand的输出钳位到指定范围通常会导致结果出现偏差。具体而言,如果发生器的范围(在C或C ++的情况下为RAND_MAX)不是您要钳制的范围的倍数,则某些输出将比其他输出更频繁地发生。为了比较,考虑尝试在3个孩子之间平均分配11个糖果(不破坏任何碎片)。你能做到的唯一方法就是不要分发一些糖果。同样,使用随机数生成器,在输出中获得均匀分布的唯一方法是不使用某些输入。
int rand_lim(int limit) {
/* return a random number between 0 and limit inclusive.
*/
int divisor = RAND_MAX/(limit+1);
int retval;
do {
retval = rand() / divisor;
} while (retval > limit);
return retval;
}
正如asveikau在帖子中指出的那样,你通常想要使用典型线性同余生成器的高位。较低的位通常更容易预测。通过划分而不是取余数,这保留了高位。虽然这确实有一个while循环,但它通常只执行一次,很少超过两次,所以它对性能的影响非常小。
这是否值得取决于你对你产生的数字的使用 - 如果你想要一个游戏的骰子或卡片,你的孩子会玩几次,使用剩余部分通常不会伤害到事情。如果您正在尝试进行某种蒙特卡罗模拟(例如),您可能想要更加小心一点......