You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

基于双向链表实现多链表时courses数组的访问问题咨询

问题解答:无法访问courses数组的所有索引,附正确多链表实现

你现在写的list->head = *courses;代码完全没法访问courses数组的每个索引,原因很直白:*courses等价于courses[0],也就是数组的第一个元素,你把它赋值给list->head后,这个list只能关联到第一门课的链表头,和数组里剩下的34个课程节点半毛钱关系都没有,自然碰不到其他索引。

针对你想要实现的学生-课程关联多链表,我给你梳理正确的实现思路:

第一步:修正Node结构体的设计

你原来的Node只有一组next/prev指针,这只能让节点属于一个双向链表,但你的需求是每个“学生选某门课”的关联节点要同时存在于两个链表(学生的选课链表、课程的选课学生链表),所以必须给节点加两组独立的前后指针,避免链表指针冲突:

typedef int element;
typedef struct Node {
    element id_num;          // 关联的学生ID
    element course_num;      // 关联的课程号
    // 用于学生选课链表的前后指针
    struct Node *stu_next;
    struct Node *stu_prev;
    // 用于课程选课学生链表的前后指针
    struct Node *course_next;
    struct Node *course_prev;
} Node;

typedef struct List {
    Node *head;
} List;

// 课程数组:每个元素对应一门课的选课链表头
Node *courses[35];
// 学生数组:每个元素对应一个学生的选课链表头
Node *students[500];

第二步:初始化数组

在使用链表前,要把所有链表头初始化为NULL,确保链表从空状态开始:

// 初始化35门课程的链表头
for (int i = 0; i < 35; i++) {
    courses[i] = NULL;
}
// 初始化500个学生的链表头
for (int i = 0; i < 500; i++) {
    students[i] = NULL;
}

第三步:实现“学生选课”的添加逻辑

当某个学生选了某门课,我们需要创建一个关联节点,同时把它插入到学生的选课链表和课程的选课学生链表中,这样两个链表就能互通了:

// 创建新的学生-课程关联节点
Node* create_student_course_link(int s_id, int c_id) {
    Node* new_node = (Node*)malloc(sizeof(Node));
    if (new_node == NULL) {
        printf("内存分配失败!\n");
        exit(1);
    }
    new_node->id_num = s_id;
    new_node->course_num = c_id;
    // 初始化两组指针为NULL
    new_node->stu_next = new_node->stu_prev = NULL;
    new_node->course_next = new_node->course_prev = NULL;
    return new_node;
}

// 将节点添加到学生的选课链表(尾插法,保持顺序)
void add_to_student_list(int s_id, Node* node) {
    Node* head = students[s_id];
    if (head == NULL) {
        students[s_id] = node;
        return;
    }
    // 找到学生链表的最后一个节点
    Node* temp = head;
    while (temp->stu_next != NULL) {
        temp = temp->stu_next;
    }
    temp->stu_next = node;
    node->stu_prev = temp;
}

// 将节点添加到课程的选课学生链表(尾插法)
void add_to_course_list(int c_id, Node* node) {
    Node* head = courses[c_id];
    if (head == NULL) {
        courses[c_id] = node;
        return;
    }
    // 找到课程链表的最后一个节点
    Node* temp = head;
    while (temp->course_next != NULL) {
        temp = temp->course_next;
    }
    temp->course_next = node;
    node->course_prev = temp;
}

// 调用示例:学生100选课程5
Node* new_link = create_student_course_link(100, 5);
add_to_student_list(100, new_link);
add_to_course_list(5, new_link);

第四步:访问courses数组的所有索引

想要遍历每门课的选课学生,直接循环遍历courses数组的索引即可:

// 遍历所有课程的选课学生列表
for (int c_id = 0; c_id < 35; c_id++) {
    printf("课程%d的选课学生:", c_id);
    Node* current = courses[c_id];
    while (current != NULL) {
        printf("%d ", current->id_num);
        current = current->course_next; // 用课程专属的next指针遍历
    }
    printf("\n");
}

同理,想要查看某个学生的所有选课,直接访问students数组对应索引的链表:

int target_student_id = 100;
printf("学生%d的选课列表:", target_student_id);
Node* current = students[target_student_id];
while (current != NULL) {
    printf("%d ", current->course_num);
    current = current->stu_next; // 用学生专属的next指针遍历
}
printf("\n");

内容的提问来源于stack exchange,提问作者Sangeui

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.05.28 09:38:18