有没有一个函数生成一个随机int数在C?或者我必须使用第三方库?


当前回答

#include <stdio.h>
#include <dos.h>

int random(int range);

int main(void)
{
    printf("%d", random(10));
    return 0;
}

int random(int range)
{
    struct time t;
    int r;

    gettime(&t);
    r = t.ti_sec % range;
    return r;
}

其他回答

<stdlib.h>中的rand()函数返回一个介于0和RAND_MAX之间的伪随机整数。你可以使用srand(unsigned int seed)来设置种子。

通常的做法是将%操作符与rand()结合使用以获得不同的范围(但请记住,这在一定程度上破坏了一致性)。例如:

/* random int between 0 and 19 */
int r = rand() % 20;

如果你真的在乎一致性,你可以这样做:

/* Returns an integer in the range [0, n).
 *
 * Uses rand(), and so is affected-by/affects the same seed.
 */
int randint(int n) {
  if ((n - 1) == RAND_MAX) {
    return rand();
  } else {
    // Supporting larger values for n would requires an even more
    // elaborate implementation that combines multiple calls to rand()
    assert (n <= RAND_MAX)

    // Chop off all of the values that would cause skew...
    int end = RAND_MAX / n; // truncate skew
    assert (end > 0);
    end *= n;

    // ... and ignore results from rand() that fall above that limit.
    // (Worst case the loop condition should succeed 50% of the time,
    // so we can expect to bail out of this loop pretty quickly.)
    int r;
    while ((r = rand()) >= end);

    return r % n;
  }
}

如果您需要比stdlib提供的质量更好的伪随机数,请检查Mersenne Twister。它也更快。示例实现有很多,例如这里。

我的极简解决方案应该适用于范围内的随机数[min, max)。在调用函数之前使用srand(time(NULL))。

int range_rand(int min_num, int max_num) {
    if (min_num >= max_num) {
        fprintf(stderr, "min_num is greater or equal than max_num!\n"); 
    }
    return min_num + (rand() % (max_num - min_num));
} 

如果你需要安全的随机字符或整数:

正如在如何在各种编程语言中安全地生成随机数中提到的,你会想要做以下事情之一:

使用libsodium的randombytes API 重新实现你自己需要的libsodium的sysrandom实现,非常小心 更广泛地说,使用/dev/urandom,而不是/dev/random。而不是OpenSSL(或其他用户空间prng)。

例如:

#include "sodium.h"

int foo()
{
    char myString[32];
    uint32_t myInt;

    if (sodium_init() < 0) {
        /* panic! the library couldn't be initialized, it is not safe to use */
        return 1; 
    }


    /* myString will be an array of 32 random bytes, not null-terminated */        
    randombytes_buf(myString, 32);

    /* myInt will be a random number between 0 and 9 */
    myInt = randombytes_uniform(10);
}

Randombytes_uniform()是加密安全且无偏倚的。

注意:为了安全性,不要使用rand()。如果您需要加密安全的号码,请参阅此答案。

#include <time.h>
#include <stdlib.h>

srand(time(NULL));   // Initialization, should only be called once.
int r = rand();      // Returns a pseudo-random integer between 0 and RAND_MAX.

在Linux上,您可能更喜欢使用random和srandom。