与实例绑定的确定性随机数生成器(与线程无关)

时间:2011-06-24 12:09:36

标签: c++ multithreading random generator

这里已经很好地涵盖了随机数字,所以我会保持简短。

我使用srandrand在模拟中生成一些确定性随机数。但是,当在不同的线程上同时运行多个模拟时,单个序列会变得混乱并变得不确定,因为所有线程都从同一个池中抽取。有没有一种简单的方法来“绑定”rand从特定实例中提取?或者我是否必须切换到Boost.Random

之类的东西

6 个答案:

答案 0 :(得分:4)

在Linux上,rand_rrand的可重入版本,但它是一个相当弱的PRNG,因此可能需要使用*rand48_r函数族中的某些内容。

rand_s是Windows上rand的可重入版本,但由于其状态为无符号整数,因此它也必然非常弱。

长话短说,你可能会选择Boost.Random。

答案 1 :(得分:4)

你的编译器很可能已经有了类似Boost.Random的东西。

C ++ 0x包含一个基于Boost.Random的<random>标题(此处和那里稍作调整)。

在此之前,TR1是一组“半标准”库,也可用于大多数编译器,其中包含几乎相同的<random>标题。

答案 2 :(得分:4)

我强烈建议使用<random><tr1/random>对高质量PRNG类进行细粒度访问,您可以在每个线程中实例化一个,完全控制其种子,从而产生随机序列号。

答案 3 :(得分:2)

您可以使用此代码,为每个线程保留rnd_state结构。您可以使用rand()初始化rnd_state。这只是一个想法,这是一个合理的RNG。

从linux内核源代码(random32.c)

rnd_state中的值应该初始化为:s1&gt; 1,s2> 7,s3&gt; 15。

该论文声称这是一个最大度等分的组合Tausworthe发生器 基于GNU Scientific Library 1.5(2004年6月30日)的代码

struct rnd_state {
    u32 s1, s2, s3;
};

static u32 __random32(struct rnd_state *state)
{
#define TAUSWORTHE(s,a,b,c,d) ((s&c)<<d) ^ (((s <<a) ^ s)>>b)

    state->s1 = TAUSWORTHE(state->s1, 13, 19, 4294967294UL, 12);
    state->s2 = TAUSWORTHE(state->s2, 2, 25, 4294967288UL, 4);
    state->s3 = TAUSWORTHE(state->s3, 3, 11, 4294967280UL, 17);

    return (state->s1 ^ state->s2 ^ state->s3);
}

学术界:http://www.iro.umontreal.ca/~lecuyer/myftp/papers/tausme.ps

答案 4 :(得分:0)

正在向标准库中添加一堆PRNG。另一个选择是为每个线程预生成一个大的数字池,然后一次发出一个。

答案 5 :(得分:0)

我的C ++随机数库RandomLib的文档包含 在OpenMP中使用并行数字流的说明;看到 http://randomlib.sourceforge.net/html/parallel.html。你可能是 能够使那里提出的想法适应您的应用。