【问题标题】:How to generate a well distributed normal distribution with a Sobol sequence in c++?如何在 C++ 中使用 Sobol 序列生成分布良好的正态分布?
【发布时间】:2017-01-20 16:15:00
【问题描述】:

我有以下代码:

#include <iostream>
#include <vector>
#include <random>
// #include "halton.cpp"
#include "sobol.cpp"

int main()
{
  int n=5000;
  double* thisV;
  thisV = i8_sobol_generate(1,n,0);

  std::mt19937 generator;
  std::normal_distribution<double> distribution(0,1.0);
  for (int i=0; i<n; i++) {
    generator.seed(thisV[i]);
    std::cout << distribution(generator) << std::endl;
  }

  return 0;
}

我在site (Sobol) 上使用以下代码生成了一个低差异序列。 我用它来播种生成器。但是输出有点奇怪。有人可以帮我吗?

输出:

1.12279
0.302805
1.12279
0.302805
1.12279
0.302805
1.12279
0.302805
1.12279
0.302805
1.12279
0.302805
1.12279
0.302805
1.12279
0.302805
...

【问题讨论】:

  • thisV[i] 中的值是否正确?
  • 我没有安装你的库,但我可以告诉你,每次迭代都为生成器播种可能不是你想要做的。播种一次,让它运行它的过程。如果您坚持使用自己的生成器,请不要费心通过std::mt19937 并实现自己的生成器类。
  • @KamilKoczurek:是的,thisV 有一个正确的 sobol 序列。
  • @FrançoisAndrieux:我认为你给了我正确的方法。是否有一些关于实现自己的生成器类的信息?
  • 事实证明,您无法使用 C++ 分布的正常(有效)方式从 Sobol 序列生成自定义分布。您必须使用其他更原始的方法。在这里查看我的答案stats.stackexchange.com/a/222538/122461

标签: c++ sequence normal-distribution seeding


【解决方案1】:

没有看到 sobol.cpp 文件的内容,我无法告诉你为什么你会得到这些确切的数字, 然而 每次循环时都要重新播种生成器。

如果是 std::mt19937 生成器;

  std::normal_distribution<double> distribution(0,1.0);
  for (int i=0; i<n; i++) {
    generator.seed(thisV[i]); //<------------
    std::cout << distribution(generator) << std::endl;
  }

如果种子在两个值之间交替,您将获得您所看到的行为。

顺便说一句 - 通常#include 一个头文件(而不是一个 cpp 文件)同时将 cpp 文件包含在你的 rmake 文件/项目中。


此外,如果你看看你是如何调用代码的,

thisV = i8_sobol_generate(1,n,0);

我们尚未阐明参数的含义。

如果您点击您拥有的链接,则会对源代码进行一些测试(哇!)。 一、调用,测试sorbol08,循环如下:

for (dim_num = 2;dim_num

// <snip>

for ( i = 0; i <= 110; i++ )
{
  seed_in = seed;
  i8_sobol ( dim_num, &seed, r );

// ....

你调用的函数,

double *i8_sobol_generate ( int m, int n, int skip )

发送 1 作为第一个参数。这会调用测试函数,使用这个值。

我怀疑你应该因此尝试更高的维度 - 它确实循环非常快。

请务必包含 .hpp 文件而不是 cpp 文件。 查看测试以获取有关使用的线索。

【讨论】:

  • 问题是我不太确定如何使用sobol序列来生成这个分布良好的正态分布。
  • 经过反思,我还没有具体回答这个问题。
猜你喜欢
  • 1970-01-01
  • 2016-09-13
  • 2020-06-18
  • 2018-06-22
  • 2012-03-15
  • 1970-01-01
  • 2018-05-15
  • 2022-11-19
  • 1970-01-01
相关资源
最近更新 更多