我不明白为什么每次输出相同的数字,即使每次输出不同的数字也是如此。 rand()%10 + 1,应该随机输出一个1到10之间的数字,但是我的代码每次都只输出相同的精确5个数字。
#include <iostream>
#include <cstdlib>
using namespace std;
int main()
{
int v1;
for(v1=0; v1 < 10; v1++) {
v1 = rand() % 10 + 1;
cout << v1 << endl;
}
return 0;
}
答案 0 :(得分:3)
您的代码的预期目标充其量是粗略的,并且您的问题描述没有任何帮助。代码本身可以采用多种方式。我认为,您正在尝试从均匀分布中绘制十个随机数。现代化的方法是这样的:
简单均匀的分布
#include <iostream>
#include <random>
int main()
{
std::mt19937 prng{ std::random_device{}() };
std::uniform_int_distribution<> dist(1, 10);
for (int i = 0; i < 10; ++i)
std::cout << dist(prng) << ' ';
std::cout.put('\n');
}
请注意,std::mt19937
是mersenne-twister prng的种子,它是使用std::random_device
通过库接口连接到某些熵源的。然后使用该prng来馈送std::uniform_int_distribution
的非平凡机制,这仅限于域{1..10}。请注意,这不不会阻止重复。下面显示了一些示例运行(尝试时最好有所不同):
输出(可变)
7 8 3 4 4 5 8 5 5 3
无需替换的选择
如果相反,您对绘制随机选择而不进行重复感兴趣,可以通过多种方法来完成,但是我更喜欢这样的小型域,那就是简单地对数字进行排序,随机洗牌,然后迭代到绘制随机顺序。再次,我们将使用适当播种的mersenne-twister prng,但这一次,我们将其用作由库提供的随机播放序列的随机源,该序列填充了非常有限的域,可从中进行绘制:
#include <iostream>
#include <random>
#include <vector>
#include <numeric>
#include <algorithm>
int main()
{
std::mt19937 rng{ std::random_device{}() };
std::vector<int> vec(10);
std::iota(vec.begin(), vec.end(), 1);
std::shuffle(vec.begin(), vec.end(), rng);
for (auto x : vec)
std::cout << x << ' ';
std::cout.put('\n');
}
输出(可变)
6 7 10 2 4 8 3 1 5 9
上面使用的重要功能:
std::iota
是一种简单的升序数字序列生成算法std::shuffle
是一种随机随机播放算法,它利用您提供的RNG源执行随机播放操作。您的代码
以上两种方法都比您似乎想做的要好。 Bias introduced with modulo against rand()
可能是一个真正的问题,只有您才能确定是否真正重要。如果您想防止这种情况,请使用我之前介绍的方法之一(适合您的需要)。
也就是说,您的代码可能 仅缺少适当的种子。根据库标准,在与rand()
一起查看之前,对srand
的任何调用都将表现为好像使用了srand(1)
。这就解释了您每次运行都会产生的重复结果。假设您同时使用v1
作为控制循环变量和来自rand
模运算的数据持有人本身就是一个错误,那么解决这两个问题的方式将是这样:>
#include <iostream>
#include <cstdlib>
#include <ctime>
int main()
{
std::srand(static_cast<unsigned>(std::time(nullptr)));
for (int i = 0; i < 10; ++i)
std::cout << 1 + std::rand() % 10 << ' ';
std::cout.put('\n');
}
输出(可变)
9 1 10 6 8 7 5 9 4 10
也就是说,我警告不要这样做。您可以在很多事情上犯错误,并且偏见总是在后台等待您咬。按保证使用其他方法之一
答案 1 :(得分:2)
您需要使用此
var canvas = document.getElementById("mycanvas");
var ctx = canvas.getContext("2d");
var p = { x: 25, y: 25 };
var velo = 3,
corner = 50,
rad = 20;
var ball = { x: p.x, y: p.y };
var moveX = Math.cos((Math.PI / 180) * corner) * velo;
var moveY = Math.sin((Math.PI / 180) * corner) * velo;
function DrawMe() {
ctx.clearRect(0, 0, 400, 300);
if (ball.x > canvas.width - rad || ball.x < rad) moveX = -moveX;
if (ball.y > canvas.height - rad || ball.y < rad) moveY = -moveY;
ball.x += moveX;
ball.y += moveY;
ctx.beginPath();
ctx.fillStyle = "red";
ctx.arc(ball.x, ball.y, rad, 0, Math.PI * 2, false);
ctx.fill();
ctx.closePath();
}
setInterval(DrawMe, 10);
答案 2 :(得分:-1)
rand()是C或C ++函数,它的编码方式使得每次我们编译和运行程序时,我们的输出必须是相同的数字序列。 有关更多信息,请参考此:rand() and srand() in C/C++ - GeeksforGeeks 这是rand - C++ Reference - Cplusplus.com
对于您的程序,您正在使用随机数更新迭代器变量,因此您应为此声明一个新变量,并根据时间使用srand(time(0))作为种子,因此您的代码应为:
#include <iostream>
#include <cstdlib>
using namespace std;
int main()
{
int v1,v2;
srand(time(0));
for(v1=0; v1 < 10; v1++) {
v2 = rand() % 10 + 1;
cout << v2 << endl;
}
return 0;
}