首页
学习
活动
专区
圈层
工具
发布
社区首页 >问答首页 >将mt19937与random_device作为静态类成员使用时出错

将mt19937与random_device作为静态类成员使用时出错
EN

Stack Overflow用户
提问于 2015-08-18 11:54:41
回答 1查看 5.8K关注 0票数 3

我有一个名为RandomNumberGenerator的类,我希望使用mt19937算法生成一个随机数。

我正在创建一个random_device对象,作为种子工作。

当我编译时,我收到一个错误,上面写着:

"No member named generate in std::__1::random_device".

我无法理解这个错误。也许我在初始化random_device和mt19937的对象时做错了什么,但我无法弄清楚到底出了什么问题。

谢谢你帮忙..。

RandomNumberGenerator.h

代码语言:javascript
复制
class RandomNumberGenerator
{
    static std::random_device   m_rd;
    static std::mt19937         m_rng;
public:
    static double getRandomNumber(const double& rangeStart, const double& rangeEnd);
};

RandomNumberGenerator.cpp

代码语言:javascript
复制
#include "RandomNumberGenerator.h"

std::random_device   RandomNumberGenerator::m_rd;
std::mt19937         RandomNumberGenerator::m_rng(RandomNumberGenerator::m_rd);

double RandomNumberGenerator::getRandomNumber(const double& rangeStart, const double& rangeEnd)
{
    std::uniform_real_distribution<> randomizer(rangeStart, rangeEnd);
    return randomizer(m_rng);
}
EN

回答 1

Stack Overflow用户

发布于 2015-08-18 12:38:23

啊,你只错过了一件小东西。

代码语言:javascript
复制
std::mt19937 RandomNumberGenerator::m_rng(RandomNumberGenerator::m_rd);

上面的行是发送实例,而不是种子。因此,它必须有一个generate函数来提供种子,而它没有。只要改变这条线来调用函子,一切就都好了。

代码语言:javascript
复制
std::mt19937 RandomNumberGenerator::m_rng(RandomNumberGenerator::m_rd());

注:

另一个要注意的事项是,您正在为每个调用分配一个新的std::uniform_real_distribution。虽然分发对象重量很轻,但是考虑让它也是静态的,只要rangeStartrangeEnd对后续调用保持不变。然而,如果您做了这个决定,初始化范围值将是一个更困难的要求。

如果您的程序在整个生命周期中没有使用这个类,请考虑将它作为一个实例类,并在ctor上使用这个范围,允许在生成数字之后进行完全清理。

希望这能有所帮助。

编辑:

如果您确实希望这是静态的,另一个选项是分配并彻底清除函数中的所有对象,这些对象将填充所有所需的值,类似于以下内容:

代码语言:javascript
复制
template<typename T, typename DISTRIBUTION_T>
static void fill(T* buffer, uint32_t const count, T const min, T const max)
{
    ASSERT(buffer);
    ASSERT(count);
    ASSERT(max > min);

    std::random_device randomDevice { };
    std::mt19937_64 twisterEngine { randomDevice() };
    DISTRIBUTION_T distribution(min, max);
    for (uint32_t i = 0u; i < count; ++i)
        buffer[i] = distribution(twisterEngine);
}

然后将其用于各种类型,如下所示:

代码语言:javascript
复制
uint32_t const COUNT = 31u;
double realValues[COUNT];
uint32_t intValues[COUNT];

RandomNumberGenerator::fill<double, std::uniform_real_distribution<double>>(realValues, COUNT, 100.0, 200.0);
RandomNumberGenerator::fill<uint32_t, std::uniform_int_distribution<uint32_t>>(intValues, COUNT, 100u, 200u);

如果这看起来像一个丑陋的接口,那么将fill设置为私有,并提供干净的公共方法来提供您希望支持的几种类型。

票数 4
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/32071721

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档