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

如何在C语言中用realloc删除动态数组中指定ID的学生元素?

学生管理程序删除功能的问题修复

原代码的删除功能存在几个关键问题,直接导致数据重复、乱码:

  1. 遍历逻辑错误:找到匹配ID后立即修改std(当前学生总数),但循环仍继续执行,会遍历已经缩小的数组,引发越界或重复处理
  2. memmove参数混乱:源地址和目标地址搞反,且size1未随学生数更新,偏移量计算完全错误
  3. 元素移动冗余:先执行ptr[i] = ptr[i+1]又调用memmove,重复操作导致数据覆盖混乱
  4. 边界情况未处理:未判断数组是否已初始化(ptr为NULL)、ID不存在的情况

修正后的删除分支代码

else if (x == 3) {
    if (ptr == NULL) {
        printf("Student list not initialized yet!\n");
        continue;
    }
    printf("Give the ID you wish to delete:\n");
    scanf("%d", &k);
    int found = 0;
    for (i = 0; i < std; i++) {
        if (k == ptr[i].id) {
            // 将删除位置后的元素整体往前移动一位
            memmove(&ptr[i], &ptr[i+1], (std - i - 1) * sizeof(student));
            // 缩小数组容量,用临时指针接收避免内存泄漏
            student *temp = realloc(ptr, (std - 1) * sizeof(student));
            if (temp != NULL) {
                ptr = temp;
            } else {
                printf("Memory reallocation failed!\n");
                break;
            }
            std--; // 更新当前学生总数
            found = 1;
            printf("Student with ID %d deleted successfully.\n", k);
            break; // ID唯一,找到后直接退出循环
        }
    }
    if (!found) {
        printf("Student with ID %d not found.\n", k);
    }
}

额外优化点

  1. 初始化分支的错误处理:添加malloc失败判断,同时释放旧内存避免泄漏
if (x == 1) {
    printf("How many new students? ");
    scanf("%d", &std);
    // 释放之前存在的内存
    if (ptr != NULL) {
        free(ptr);
        ptr = NULL;
    }
    ptr = malloc(std * sizeof(student));
    if (ptr == NULL) {
        printf("Memory allocation failed!\n");
        std = 0;
        continue;
    }
    for (i = 0; i < std; i++) {
        printf("Enter detail of student #%d\n", (i + 1));
        ptr[i].id = i + 1;
        printf("Enter first name: ");
        scanf("%s", ptr[i].name);
        printf("Enter last name: ");
        scanf("%s", ptr[i].surname);
        printf("Enter semester: ");
        scanf("%d", &ptr[i].semester);
        printf("Enter grade: ");
        scanf("%f", &ptr[i].grade);
    }
}
  1. 退出时释放内存:在while循环结束后添加free(ptr);,彻底避免内存泄漏

核心逻辑说明

  • 删除元素时,用memmove高效地将删除位置后的所有元素整体前移,覆盖待删除项
  • 用临时指针接收realloc返回值,防止内存分配失败时丢失原数组指针
  • 找到匹配ID后立即退出循环,避免不必要的遍历
  • 增加初始化检查和ID不存在提示,提升程序健壮性

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.08.06 15:25:25