C++随机数方面的一次bug排查
C++随机数方面的一次bug排查
背景
练习十大排序算法的时候原本使用的是固定的数组,后来觉得总用同一套数据测试可能会掩盖问题,所以改成了随机生成数组。
代码如下
// try.cpp
#include <cstdlib> /* srand, rand */
#include <ctime> /* time */
#include <vector>
#define vector_size 8
using std::vector;
int main(){
int randint = 0;
srand (time(0));
vector<int> array;
for(i = 0; i < vector_size; i++){
randint = rand() % 100 + 1;
array.push_back(randint);
}
cout << "输入";
for(i = 0; i != vector_size; i++){
cout << v[i] << ' ';
}
cout << endl;
}
一些新奇的想法
感觉生成随机数以后应该还会用到,所以写一个my_tricks_stl.h作为自己以后一些小把戏的标准库,包括但不限于生成随机数。。。。。
// my_tricks_stl.h
#ifndef MY_TRICKS_STL_H
#define MY_TRICKS_STL_H
#include <cstdlib> /* srand, rand */
#include <ctime> /* time */
namespace my_tricks{
int rand_tricks(){
srand (time(0));
int random = rand(); // generate random
return random;
}
} // namespace my_tricks
#endif
// try.cpp
for(i = 0; i < vector_size; i++){
randint = my_tricks::rand_tricks() % 100 + 1;
array.push_back(randint);
}
奇怪的事发生了,生成的随机数竟然完全一样。伪随机数与真随机数笔者还是了解的,但这每次调用函数生成的应该不一样的啊,为什么这样
尝试与困惑
class rand_{
public:
rand_(){
srand (time(0)); // initialize random seed
}
int rand_t(){
int random = rand(); // generate random
return random;
}
};
class rand_{
public:
void rand__(){
srand (time(0)); // initialize random seed
}
int rand_t(){
rand__();
int random = rand(); // generate random
return random;
}
};
class rand_{
public:
int rand_t(){
srand (time(0)); // initialize random seed
int random = rand(); // generate random
return random;
}
};
上面三段代码你猜那段是正确的?
聪明的你肯定猜错了,聪明又勤奋的你肯定猜对了。第一段是对的,第二第三段代码生成的随机数都是相同的。
到这里聪明的你肯定发现了华点。第一段代码的 srand() 在构造函数中,生成n个随机数只调用了一次,第二第三段代码则会调用 n 次。这一现象背后的原因肯定与srand() 的底层机制有关。按理说我该去看看源码了,但是十大排序都不能顺畅写出来的菜鸡我还是去学习吧,先把春招搞定再填这个坑。
第一张图是大佬,第二张的才是我。
最后的解决方法
class rand_{
private:
rand_(){
srand (time(0)); // initialize random seed
}
public:
int rand_t(){
int random = rand(); // generate random
return random;
}
};
rand_ r;
int rand_tricks(){
int random = r.rand_t(); // generate random
return random;
}