繁体   English   中英

调用RandGenerator的隐式删除的复制构造函数

[英]Call to implicitly-deleted copy constructor of RandGenerator

我有一个类创建一个对象来生成一定范围内的随机数,代码看起来像这样

#pragma once

#include <random>

class RandGenerator
{
public:
    RandGenerator();
    RandGenerator(const float& min, const float& max);
    float nextRandom();

private:
    std::random_device mRandDevice;
    std::mt19937 mGenerator;
    std::uniform_real_distribution<> mSampler;
};

RandGenerator::RandGenerator() : RandGenerator(0.f, 1.f)
{}

RandGenerator::RandGenerator(const float& min, const float& max)
{
    mGenerator = std::mt19937(mRandDevice());
    mSampler = std::uniform_real_distribution<>(min, max);
}

float RandGenerator::nextRandom()
{
    return mSampler(mGenerator);
}

然后,我创建了另一个类,它具有一个RandGenerator实例,可以从单位范围中进行采样(非常简单和天真,但仅用于学习目的),看起来像

#pragma once

#include "randgenerator.h"
#include "point.h"

class UnitSphereSampler
{
public:
    UnitSphereSampler();
    Point nextSample();

private:
    RandGenerator mRandGenerator;
};

UnitSphereSampler::UnitSphereSampler() :
mRandGenerator(RandGenerator(-1.f, 1.f)) // ERROR HERE
{
}

Point UnitSphereSampler::nextSample()
{
    Point p;

    do
    {
        float x = mRandGenerator.nextRandom();
        float y = mRandGenerator.nextRandom();
        float z = mRandGenerator.nextRandom();
        p = Point(x, y, z);
    } while ((p - Point(0.f)).normSq() >= 1.f);

    return p;
}

从我在这个c ++参考中可以看到对象std::random_device没有复制构造函数,这就是我在UnitSphereSampler类的构造函数中使用mRandGenerator(RandGenerator(-1.f, 1.f))的原因。

这在VS2013中运行良好但是,我试图在OS X Sierra中编译并得到错误

Call to implicitly-deleted copy constructor of RandGenerator

我试图指出复制正在进行的地方,但我似乎无法找到它,我是在寻找正确的东西还是我还缺少其他东西? 我认为我初始化RandGenerator的方式避免了对复制构造函数的调用。 有什么建议吗?

我认为它确实与mRandGenerator(RandGenerator(-1.f, 1.f))行中生成的副本mRandGenerator(RandGenerator(-1.f, 1.f))

分析一下它会创建一个RandGenerator rvalue,我相信它会调用编译器隐式定义的move构造函数,即RandGenerator(const RandGenerator&& rg)

现在,即使调用了RandGenerator的移动构造函数,它也必须复制对象std::random_device ,这是不允许的,因此会产生错误。

我刚刚意识到这一点但不确定,我邀请更有经验的人来表达他们的想法和/或完成这个答案。

与此同时,我将使用一个指向RandGenerator的指针,这将避免执行复制和完美编译,即

UnitSphereSampler::UnitSphereSampler()
{
    mRandGenerator = new RandGenerator(-1.f, 1.f);
}

其中mRandGenerator的类型为RandGenerator*

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM