uniform_int_distribution在这里使用错了? (我的结果似乎不均匀分布)

时间:2015-03-21 13:52:48

标签: c++ c++11 random distribution

版本3 将生成器移动到类中。这次我的新随机数生成技术是否正确?

template<typename T = int>
    class MyRandomGenerator
    {
    public:
        MyRandomGenerator()
        {
            std::random_device rd;
            gen = std::mt19937{rd()};
        }

        T getNumber(const T& From, const T& To)
        {
            std::uniform_int_distribution<T> dist(From, To);
            return dist(gen);
        }
    private:
        std::mt19937 gen;
    };

这是我的新位置计算器:

auto calculate_x_position = [&]() ->sf::Uint32 {return RandGen.getNumber(0, W - 1); };
auto calculate_y_position = [&]() ->sf::Uint32 {return RandGen.getNumber(0, H - 1); };

与以前相同的模式/问题: enter image description here

版本2 每张地图每秒创建〜3张地图,每张地图10.000颗。结果仍然相同。此外,更清楚的是,地图的顶部有一个枢轴。示例:enter image description here

原始问题: 我开始尝试绘制一个简单的星图。为此,我首先计算星星的x和y位置。 X和Y在窗口的宽度和高度范围内。

这是我的随机数生成函数:

    template<typename T>
    T getRandomNumberBetween(const T& Min, const T& Max)
    {
        static std::random_device rd;
        static std::uniform_int_distribution<T> dist{Min, Max};
        return dist(rd);
    }

我这样用它:

auto calculate_x_position = std::bind(inc::getRandomNumberBetween<sf::Uint32>, 0, Width-1);
    auto calculate_y_position = std::bind(inc::getRandomNumberBetween<sf::Uint32>, 0, Height-1);
x = calculate_x_position(); //...

但是当我一遍又一遍地绘制我的地图时,在我看来,大多数星星往往都是一个枢轴。例如。大部分的星星都在我窗户的上半部分。

示例:

enter image description here

我使用它错了或在这里有错误的期望吗?...因为here它说:

  

此分布在[a,b]范围内产生随机整数   可能的价值具有相同的生产可能性。

亲切的问候

2 个答案:

答案 0 :(得分:4)

统一分布并不意味着您将在屏幕的每个象限中获得相同的金额;这意味着每个点出现的机会均等。因此,如果您进行简单的50:50试验,并不意味着您将得到50:50的结果。

然而,如果你用1,000,000颗星进行测试,它们很可能几乎均匀分布。对我来说,这似乎是样本量的错误

答案 1 :(得分:0)

您可以通过多种方式改进代码。引擎只能创建一次,而不是每次想要一个随机数。而且您通常不想使用std::default_random_engine,因为它可能默认为std::rand。更好的默认值是std::mt19937。我的示例来自The bell has tolled for rand()

#include <random>

std::mt19937& prng_engine()
{
  thread_local static std::random_device rd{};
  thread_local static std::mt19937 engine{rd()};

  // Or you can replace the two previous lines with:
  //thread_local static std::mt19937
  //  prng{std::random_device{}()};

  return engine;
}

template<typename T>
T getRandomNumberBetween(T Min, T Max)
{
    thread_local static std::uniform_int_distribution<T> dist{Min, Max};
    return dist(prng_engine());
}