c语言如何随机数不重复

c语言如何随机数不重复

C语言随机数不重复的实现方法主要包括:使用数组记录已生成的数、使用标记数组、使用动态数据结构、通过洗牌算法。其中,洗牌算法(如Fisher-Yates洗牌算法)在处理大量数据时尤为高效。以下将详细讲解这一方法。

一、使用数组记录已生成的数

方法概述

这种方法通过创建一个数组来记录已生成的随机数,每次生成新的随机数时,检查该数组是否包含该数,如果包含则重新生成,直到生成一个新的未被记录的数。

实现步骤

  1. 创建一个数组用于存储已生成的随机数。
  2. 每次生成新的随机数时,检查该数组是否包含该数。
  3. 如果数组包含该数,则重新生成随机数,直到生成一个新的未被记录的数。
  4. 将新的随机数存入数组中。

代码示例

#include <stdio.h>

#include <stdlib.h>

#include <time.h>

#define MAX_NUM 100 // 生成随机数的上限

#define COUNT 10 // 需要生成的随机数个数

int main() {

int numbers[COUNT];

int count = 0;

srand(time(0));

while (count < COUNT) {

int num = rand() % MAX_NUM;

int i;

for (i = 0; i < count; i++) {

if (numbers[i] == num) {

break;

}

}

if (i == count) {

numbers[count++] = num;

}

}

for (int i = 0; i < COUNT; i++) {

printf("%d ", numbers[i]);

}

return 0;

}

二、使用标记数组

方法概述

标记数组用于记录某个数是否已经被生成过。通过标记数组的方式,可以快速判断一个数是否已经生成过,从而避免重复生成。

实现步骤

  1. 创建一个标记数组,用于标记某个数是否已生成。
  2. 每次生成新的随机数时,通过标记数组检查该数是否已生成。
  3. 如果该数未被生成,则将其标记为已生成并记录下来。

代码示例

#include <stdio.h>

#include <stdlib.h>

#include <time.h>

#define MAX_NUM 100 // 生成随机数的上限

#define COUNT 10 // 需要生成的随机数个数

int main() {

int flags[MAX_NUM] = {0};

int numbers[COUNT];

int count = 0;

srand(time(0));

while (count < COUNT) {

int num = rand() % MAX_NUM;

if (!flags[num]) {

flags[num] = 1;

numbers[count++] = num;

}

}

for (int i = 0; i < COUNT; i++) {

printf("%d ", numbers[i]);

}

return 0;

}

三、使用动态数据结构

方法概述

通过使用链表、集合等动态数据结构,可以有效管理已生成的随机数,并快速查找和插入新的随机数。

实现步骤

  1. 使用链表或集合存储已生成的随机数。
  2. 每次生成新的随机数时,检查数据结构中是否包含该数。
  3. 如果不包含,则将新的随机数插入到数据结构中。

代码示例(使用链表)

#include <stdio.h>

#include <stdlib.h>

#include <time.h>

#define MAX_NUM 100 // 生成随机数的上限

#define COUNT 10 // 需要生成的随机数个数

typedef struct Node {

int data;

struct Node *next;

} Node;

Node* createNode(int data) {

Node *newNode = (Node *)malloc(sizeof(Node));

newNode->data = data;

newNode->next = NULL;

return newNode;

}

int contains(Node *head, int data) {

Node *current = head;

while (current != NULL) {

if (current->data == data) {

return 1;

}

current = current->next;

}

return 0;

}

void append(Node head, int data) {

Node *newNode = createNode(data);

if (*head == NULL) {

*head = newNode;

return;

}

Node *current = *head;

while (current->next != NULL) {

current = current->next;

}

current->next = newNode;

}

void freeList(Node *head) {

Node *tmp;

while (head != NULL) {

tmp = head;

head = head->next;

free(tmp);

}

}

int main() {

Node *head = NULL;

int numbers[COUNT];

int count = 0;

srand(time(0));

while (count < COUNT) {

int num = rand() % MAX_NUM;

if (!contains(head, num)) {

append(&head, num);

numbers[count++] = num;

}

}

for (int i = 0; i < COUNT; i++) {

printf("%d ", numbers[i]);

}

freeList(head);

return 0;

}

四、使用洗牌算法

方法概述

洗牌算法(如Fisher-Yates洗牌算法)通过随机打乱一个数组来生成一组不重复的随机数。

实现步骤

  1. 初始化一个数组,包含从0到N-1的所有数。
  2. 使用Fisher-Yates洗牌算法随机打乱该数组。
  3. 从打乱后的数组中取出前COUNT个数作为不重复的随机数。

代码示例

#include <stdio.h>

#include <stdlib.h>

#include <time.h>

#define MAX_NUM 100 // 生成随机数的上限

#define COUNT 10 // 需要生成的随机数个数

void shuffle(int *array, int n) {

if (n > 1) {

for (int i = 0; i < n - 1; i++) {

int j = i + rand() / (RAND_MAX / (n - i) + 1);

int t = array[i];

array[i] = array[j];

array[j] = t;

}

}

}

int main() {

int numbers[MAX_NUM];

for (int i = 0; i < MAX_NUM; i++) {

numbers[i] = i;

}

srand(time(0));

shuffle(numbers, MAX_NUM);

for (int i = 0; i < COUNT; i++) {

printf("%d ", numbers[i]);

}

return 0;

}

小结

上述四种方法中,使用洗牌算法在处理大量数据时尤为高效,因为它能保证生成的数不重复且时间复杂度较低。此外,标记数组动态数据结构在特定条件下也有其优势,开发者可根据具体需求选择适合的方法。

在实际项目管理中,特别是涉及复杂的研发项目时,使用合适的工具能够提高效率。比如,研发项目管理系统PingCode通用项目管理软件Worktile都能帮助团队更好地管理任务和时间。选择合适的工具和方法,不仅能解决技术难题,还能提升整体项目的成功率。

相关问答FAQs:

1. 随机数生成器如何确保生成的随机数不重复?

随机数生成器通常使用种子来生成随机数序列。种子可以是一个固定的值,也可以是一个随机的值。为了确保生成的随机数不重复,可以使用当前的系统时间作为种子,因为系统时间在每一次运行时都是唯一的。这样,每次生成的随机数序列都会不同。

2. 如何在C语言中生成不重复的随机数序列?

可以使用一个数组来保存已经生成的随机数,每次生成新的随机数时,先检查数组中是否已经存在该数,如果存在则重新生成,直到生成一个不重复的随机数为止。这样可以确保生成的随机数序列不重复。

3. 如何在C语言中生成指定范围内的不重复随机数?

可以使用一个集合来保存已经生成的随机数,每次生成新的随机数时,先检查集合中是否已经存在该数,如果存在则重新生成,直到生成一个不重复的随机数为止。同时,可以使用取余运算符和加法运算符来限制生成随机数的范围,确保生成的随机数在指定范围内。这样可以生成指定范围内的不重复随机数序列。

原创文章,作者:Edit1,如若转载,请注明出处:https://docs.pingcode.com/baike/1055080

(0)
Edit1Edit1
上一篇 2024年8月27日 下午10:11
下一篇 2024年8月27日 下午10:11
免费注册
电话联系

4008001024

微信咨询
微信咨询
返回顶部