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

C语言链表按字母顺序排序学生姓名的问题排查与实现

修复链表按姓名排序的sortlist()函数

看起来你已经有了一个雏形,但原代码存在几个关键问题:比如未处理temp1为NULL的边界情况,以及排序循环逻辑不完整。下面我会给出两种可行的实现方案,你可以根据需求选择。

方案1:交换节点数据(简单易实现)

这种方式直接交换节点里的姓名和分数数据,逻辑简单,适合学生管理这种数据量不大的场景:

#include <string.h>
// 假设你的Node结构体定义是这样的:
// struct Node {
//     char name[25];
//     int score;
//     struct Node *next;
// };
// struct Node *head; // 全局头节点

void sortlist() {
    struct Node *temp;
    struct Node *temp1;
    char temp_name[25];
    int temp_score;

    // 如果链表为空或者只有一个节点,直接返回
    if (head == NULL || head->next == NULL) {
        return;
    }

    // 冒泡排序的外层循环:遍历每个节点
    for (temp = head; temp != NULL; temp = temp->next) {
        // 内层循环:和temp之后的所有节点比较
        for (temp1 = temp->next; temp1 != NULL; temp1 = temp1->next) {
            // 按姓名字典序比较,temp的姓名比temp1大就交换
            if (strcmp(temp->name, temp1->name) > 0) {
                // 交换姓名
                strcpy(temp_name, temp->name);
                strcpy(temp->name, temp1->name);
                strcpy(temp1->name, temp_name);
                // 别忘了交换分数,不然数据对应不上!
                temp_score = temp->score;
                temp->score = temp1->score;
                temp1->score = temp_score;
            }
        }
    }
}

关键修正点:

  • 增加了边界检查:如果链表为空或只有一个节点,直接返回,避免无效遍历
  • 使用双层循环实现冒泡排序,确保每个节点都和后面所有节点比较
  • 补充了分数交换:原代码只交换了姓名,会导致姓名和分数不匹配,这是很容易忽略的细节

方案2:调整节点指针(更高效)

如果链表数据量较大,交换节点指针比交换数据更高效,不需要拷贝字符串和整数:

void sortlist() {
    struct Node **current = &head;
    struct Node *sorted = NULL; // 已排序的链表头

    if (head == NULL || head->next == NULL) {
        return;
    }

    while (*current != NULL) {
        struct Node *next_node = (*current)->next;
        struct Node **insert_pos = &sorted;

        // 找到当前节点在已排序链表中的插入位置
        while (*insert_pos != NULL && strcmp((*insert_pos)->name, (*current)->name) < 0) {
            insert_pos = &((*insert_pos)->next);
        }

        // 插入当前节点到已排序链表
        (*current)->next = *insert_pos;
        *insert_pos = *current;

        // 处理下一个未排序节点
        *current = next_node;
    }

    // 更新原链表的头节点为已排序的链表头
    head = sorted;
}

这种方式的优势:

  • 不需要拷贝数据,只调整指针,性能更好
  • 属于插入排序的变种,对部分有序的链表效率更高

测试提示

调用sortlist()前,确保你的链表已经正确构建(所有节点的next指针都正确赋值,头节点head指向第一个有效节点)。测试时可以输入几个姓名,比如"Bob"、"Alice"、"Charlie",排序后应该得到Alice -> Bob -> Charlie的顺序。

内容的提问来源于stack exchange,提问作者zhen wei sun

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.05.20 10:37:04