为什么从函数调用时 c++11 std::normal_distribution return 相同的模式?
Why c++11 std::normal_distribution return same pattern when called from a function?
我想在信号中引入高斯噪声。我研究了几个如何使用 C++11 std::normal_distribution
的示例,并且能够使用此示例实现预期的随机结果:
#include <functional>
#include <iostream>
#include <iterator>
#include <random>
int main() {
// Example data
std::vector<double> data = {1., 2., 3., 4., 5., 6.};
// Define random generator with Gaussian distribution
const double mean = 0.0;
const double stddev = 0.1;
auto dist = std::bind(std::normal_distribution<double>{mean, stddev},
std::mt19937(std::random_device{}()));
// Add Gaussian noise
for (auto& x : data) {
x = x + dist();
}
// Output the result, for demonstration purposes
std::copy(begin(data), end(data), std::ostream_iterator<double>(std::cout, " "));
std::cout << "\n";
return 0;
}
当我从 main()
多次调用 dist()
并且在不同的向量上也能很好地工作时,这个工作非常完美,但是一旦我将代码移动到一个函数中,它总是 return相同的恒定噪声模式,我想调用此函数来修改参考信号并将其分配给不同的数组或向量。这是我的代码:
void AddGaussianNoiseToPixel(std::array<short int, N_SLICES>& pixel_array, const std::array<short int, N_SLICES>& reference_pixel)
{
const float mean = 0.0;
const float stddev = 2.0;
auto dist = std::bind(std::normal_distribution<float>{mean, stddev},
std::mt19937(std::random_device{}()));
for (const auto& slice : reference_pixel)
{
pixel_array[&slice-&reference_pixel[0]] = rint(slice+dist());
}
}
我读到类似的 post: 假设这是由于种子传递给随机生成器而发生的,但事实并非如此,因为我正在传递 std::random_device{}()
到随机引擎std::mt19937()
编辑:
我在 Windows 7
中使用 MinGW-W64-builds-4.3.5
这很可能与使 std::random_device
具有确定性的 feature/bug in mingw 有关。您可以通过添加另一个熵源来避免这种情况,例如当前时间:
uint64_t seed = std::random_device{}() |
std::chrono::system_clock::now().time_since_epoch().count();
但是,更好的解决方案是只使用一个引擎和分发对象。一种简单的方法是在新函数中使用静态变量。
我想在信号中引入高斯噪声。我研究了几个如何使用 C++11 std::normal_distribution
的示例,并且能够使用此示例实现预期的随机结果:
#include <functional>
#include <iostream>
#include <iterator>
#include <random>
int main() {
// Example data
std::vector<double> data = {1., 2., 3., 4., 5., 6.};
// Define random generator with Gaussian distribution
const double mean = 0.0;
const double stddev = 0.1;
auto dist = std::bind(std::normal_distribution<double>{mean, stddev},
std::mt19937(std::random_device{}()));
// Add Gaussian noise
for (auto& x : data) {
x = x + dist();
}
// Output the result, for demonstration purposes
std::copy(begin(data), end(data), std::ostream_iterator<double>(std::cout, " "));
std::cout << "\n";
return 0;
}
当我从 main()
多次调用 dist()
并且在不同的向量上也能很好地工作时,这个工作非常完美,但是一旦我将代码移动到一个函数中,它总是 return相同的恒定噪声模式,我想调用此函数来修改参考信号并将其分配给不同的数组或向量。这是我的代码:
void AddGaussianNoiseToPixel(std::array<short int, N_SLICES>& pixel_array, const std::array<short int, N_SLICES>& reference_pixel)
{
const float mean = 0.0;
const float stddev = 2.0;
auto dist = std::bind(std::normal_distribution<float>{mean, stddev},
std::mt19937(std::random_device{}()));
for (const auto& slice : reference_pixel)
{
pixel_array[&slice-&reference_pixel[0]] = rint(slice+dist());
}
}
我读到类似的 post: 假设这是由于种子传递给随机生成器而发生的,但事实并非如此,因为我正在传递 std::random_device{}()
到随机引擎std::mt19937()
编辑:
我在 Windows 7
中使用 MinGW-W64-builds-4.3.5这很可能与使 std::random_device
具有确定性的 feature/bug in mingw 有关。您可以通过添加另一个熵源来避免这种情况,例如当前时间:
uint64_t seed = std::random_device{}() |
std::chrono::system_clock::now().time_since_epoch().count();
但是,更好的解决方案是只使用一个引擎和分发对象。一种简单的方法是在新函数中使用静态变量。