首页 > 解决方案 > C++ 相同的值是随机生成的,有两个 for 循环

问题描述

所以我在这里处理这个 for 循环:

    for (int i = 0; i < num; i++) {
        for (int i = 0; i < length; i++) {
            Str += randGen();
        }
        cout << Str << endl;
    }
}

对于上下文,整数“长度”是随机生成的字符串大小。这是我的 randGen() 函数:

static const char combination[] =
"0123456789"
"!@#$%^&*"
"ABCDEFGHIJKLMNOPQRSTUVWXYZ"
"abcdefghijklmnopqrstuvwxyz";

int stringLength = sizeof(combination) - 1;

char randGen() {

    return combination[rand() % stringLength];
}

基本上我的问题是,如果 'num' 大于一,它将打印出每个相同的开始随机生成的部分,并且不会改变。唯一一次有新的随机生成的字符是当“长度”的大小增加时,就是这样。但是,我希望所有的 STR 都完全不同。谁能帮我?

--提前谢谢--

标签: c++for-looprandomrandom-seed

解决方案


如果您想使用 获得依赖于运行时的输出rand(),则应根据运行时环境使其成为种子。正如评论中所建议的,一种简单的方法是在-loopsrand(time(NULL))之前调用一次:num

演示

srand(time(NULL));

for (int i = 0; i < num; ++i)
{
    for (int j = 0; j < length; ++j) {
        Str += randGen();
    }
    
    std::cout << Str << std::endl;
}

虽然rand()通常应该作为 Park-Miller LCG 来实现,但是,例如,如 C++ 标准草案 n4687 中所述,所使用的算法rand()完全由编译器实现定义

29.6.9 低质量随机数生成 [c.math.rand]

int rand();
void srand(unsigned int seed);

... rand的底层算法未指定。因此, rand的使用仍然是不可移植的,具有不可预测且经常受到质疑的质量和性能。

幸运的是,在 C++11 及更高版本中,我们可以使用它<random>来生成保证质量的随机性。因此,我建议您按如下方式使用它们。如果您需要更高质量的随机性,可以使用std::mt19937代替std::minstd_rand

演示

#include <random>

static constexpr char combination[] =
"0123456789"
"!@#$%^&*"
"ABCDEFGHIJKLMNOPQRSTUVWXYZ"
"abcdefghijklmnopqrstuvwxyz";

constexpr int stringLength = sizeof(combination) - 1;
std::minstd_rand gen(std::random_device{}());
std::uniform_int_distribution<std::size_t> dis(0, stringLength-1);

char randGen() {
    return combination[dis(gen)];
}

推荐阅读