C语言随机数生成(纯C代码,无库或函数)

5
我需要在C语言中生成一些随机数,用于测试和调试系统。该系统是一个自定义的硬件 (SoC),具有有限的功能集,因此我只能使用基本的数学运算。
不过,不能使用stdlib或math.h中的随机数生成器。我需要自己编写。那么是否有一种算法可以生成随机数呢?
我知道一个简单的解决方案是在我的工作站上生成数字,然后将它们嵌入到模块中,但我不想这样做。
7个回答

8

请查阅CACM 1988年10月份的Park和Miller撰写的文章。

他们提出的一般算法如下:

a = 16807;
m = 2147483647;
seed = (a * seed) mod m;
random = seed / m;

虽然这篇文章包含多个改进。


3
我猜最后一次除法应该使用浮点数,否则 random 始终为零。 - Axel Bregnsbo

5

随机数生成器基本上是一种特殊的哈希函数,它从一个起始种子递归地运行。

我在我的C#代码中使用了MurmurHash2算法,效果很好。它非常快速和简单易实现,并已经经过测试,具有良好的分布性和低碰撞率。该项目有几个不同的开源哈希函数,用C++编写,应该很容易转换为C。


* 特别指的是,对某个值运行哈希函数应该返回另一个看似随机(但确定)的值,以使输出不会形成模式。此外,返回值的分布应具有均匀分布。


“..已经被测试为非常具有密码学安全性。”绝对不是这样的!MurmurHash是一种相对较新的哈希算法,它存在许多缺陷并进行了许多调整 - 这表明该算法是薄弱的。当然,您可以使用它来生成伪随机数,但是没有人应该将其用于加密操作。 - adelphus
@adelphus——我不是密码学专家,所以我会删除这个声明,但我认为具有密码学安全性意味着具有良好的分布、低碰撞和低偏差。@Peter O.——发现得好:我确实是指均匀分布。糟糕。 - dlras2

4

1
你可以尝试使用George Marsaglia的乘法累加算法
来自维基百科的代码:
#include <stdint.h>

#define PHI 0x9e3779b9

static uint32_t Q[4096], c = 362436;

void init_rand(uint32_t x)
{
    int i;

    Q[0] = x;
    Q[1] = x + PHI;
    Q[2] = x + PHI + PHI;

    for (i = 3; i < 4096; i++)
            Q[i] = Q[i - 3] ^ Q[i - 2] ^ PHI ^ i;
}

uint32_t rand_cmwc(void)
{
    uint64_t t, a = 18782LL;
    static uint32_t i = 4095;
    uint32_t x, r = 0xfffffffe;
    i = (i + 1) & 4095;
    t = a * Q[i] + c;
    c = (t >> 32);
    x = t + c;
    if (x < c) {
            x++;
            c++;
    }
    return (Q[i] = r - x);
}

0

查看gsl库的源代码,其中实现了一些经过充分测试的算法。


0

0
你可以尝试使用Isaac,它也作为CCAN 这里的一部分提供。

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接