使用随机数据填充内存区域

时间:2017-06-02 13:47:51

标签: c random populate

我试图以有效的方式使用rand跨平台以随机方式填充数据区域。以下是我到目前为止的情况:

/**********************************************\
*          Useful macro by Glen Ragen          *
* https://stackoverflow.com/a/39920811/5223757 *
\**********************************************/
#if 1 /* So that the IDE minifies it */
#define NEEDS_BIT(N, B)     (((unsigned long)N >> B) > 0)

#define BITS_TO_REPRESENT(N)                   \
        (NEEDS_BIT(N,  0) + NEEDS_BIT(N,  1) + \
         NEEDS_BIT(N,  2) + NEEDS_BIT(N,  3) + \
                         ...
         NEEDS_BIT(N, 60) + NEEDS_BIT(N, 61) + \
         NEEDS_BIT(N, 62) + NEEDS_BIT(N, 63)   \
        )
#endif /* So that the IDE minifies it */

typedef struct {
    size_t size; /* Size in bytes */
    void *pointer;
} data;

void fill_data_with_randomness(const data data) {
    for (size_t biti = 0; biti < data.size * 8; biti += BITS_TO_REPRESENT(RAND_MAX)) {
        /* Fill data.pointer with bits from rand() */
    }
}

由于RAND_MAX是编译时常量,BITS_TO_REPRESENT(RAND_MAX)也应该是。data。由于const data的类型为data.size * 8fill_data_with_randomness应该能够优化为调用时常量,而不是在for循环的每次迭代中进行评估。

但是,位操作非常慢,RAND_MAX函数将被频繁调用。此函数应在具有格式为2 ^ n-1的fill_data_with_randomness的任何值的系统上进行编译和正确运行。什么rand()函数可以用{{1}} mness快速填充这个内存区域而不浪费位?

1 个答案:

答案 0 :(得分:4)

rand()保证至少为2 15 -1,因此只需一次调用rand()就可以通过随机性填充整个字节,除非你的体系结构具有大于15位的字节(在这种情况下,您的硬编码乘以8也会有问题)。

逐字节地进行生成是直截了当的,并且不需要钻头聪明。

就我个人而言,我不会担心会浪费比特&#34;致电git log --max-count=1 --pretty=format:'%H' COMMITKEY~1 -- path/to/file ;在大多数实现中,由该标准库函数产生的位并不值得。真正的问题是决定丢弃哪些比特,以便剩下的比特分配得相当好。如果可能的话,为了应对通常使用的劣质PRNG的范围,你应该选择中间位。

更好的解决方案可能是简单地提供您自己的PRNG;存在可移植的源代码实现,并且一些已被很好地研究。