在GSL中有许多随机生成器。例如,最大等分布的组合Tausworthe发生器的实现位于gsl / taus.c。随机种子设置在以下函数中:
static inline unsigned long
taus_get (void *vstate)
{
taus_state_t *state = (taus_state_t *) vstate;
#define MASK 0xffffffffUL
#define TAUSWORTHE(s,a,b,c,d) (((s &c) <<d) &MASK) ^ ((((s <<a) &MASK)^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);
}
static void
taus_set (void *vstate, unsigned long int s)
{
taus_state_t *state = (taus_state_t *) vstate;
if (s == 0)
s = 1; /* default seed is 1 */
#define LCG(n) ((69069 * n) & 0xffffffffUL)
state->s1 = LCG (s);
state->s2 = LCG (state->s1);
state->s3 = LCG (state->s2);
/* "warm it up" */
taus_get (state);
taus_get (state);
taus_get (state);
taus_get (state);
taus_get (state);
taus_get (state);
return;
}
我的问题是为什么他们需要六次“热身”?如果没有热身,有什么不对吗?
答案 0 :(得分:1)
六可能是任意数字。不要太小,以至于没有足够的随机性而不是那么大,以至于它减慢了启动速度。
在您发布的代码中引用的论文中没有提及它。另一篇论文(http://www0.cs.ucl.ac.uk/staff/d.jones/GoodPracticeRNG.pdf)确实讨论了“预热”随机数发生器的必要性。
基本上,当“你的种子值具有非常低的熵”时使用它。讨论见参考文件的第9页。