C语言数组元素删除异常:员工管理系统删除操作总是删除最后一个元素
C语言数组元素删除异常:员工管理系统删除操作总是删除最后一个元素
刚学C语言写数组操作遇到这种问题太正常了,我帮你把代码里的几个关键错误揪出来,看完你就明白为什么总是删最后一个元素了!
问题1:字符串移动用了判断运算符而非赋值,且字符串不能直接用=赋值
你的删除函数里这行代码是核心bug:
for (int i = pos; i < NOE; i++) Name[i] == Name[i + 1];
- 首先,
==是相等判断运算符,不是赋值!这行代码只是在判断两个字符串是否相等,完全没有做任何元素向前移动的操作。 - 其次,C语言里的字符数组(字符串)不能直接用
=赋值,必须用strcpy函数来完成字符串内容的拷贝。
这就导致循环执行后数组元素根本没挪位置,只是把NOE减了1——相当于直接“截断”了数组的最后一个元素,所以看起来总是删除了最后一个员工。
问题2:只处理了Name数组,未同步处理ID数组
你删除员工时只想着移动Name数组,但完全没管ID数组,这样后续Name和ID就会对应不上,数据直接乱掉。
问题3:缺少索引合法性检查(可选但关键)
用户输入的pos可能超出有效范围(比如负数、大于等于当前员工数),直接用的话会导致数组越界,程序轻则输出乱码,重则崩溃。
修正后的完整代码(重点看Delete函数)
#include <stdio.h> #include <string.h> #include <stdlib.h> // 全局变量(小项目临时用没问题,后续可以学用结构体+参数传递优化) char Name[100][50]; int ID[100], NOE; void Register(){ printf("\n\n请输入要注册的员工数量: "); scanf("%d", &NOE ); for (int i = 0; i < NOE; i++) { printf("\n\n请输入第%d位员工的姓名: ", i + 1); scanf("%s", Name[i]); // Name[i]本身就是字符数组首地址,不用加& printf("\n\n请输入第%d位员工的ID: ", i + 1); scanf("%d", &ID[i]); printf("\n\n注册成功!\n\n "); } printf("\n"); } // 完全修正后的删除函数 void Delete(){ if (NOE == 0) { printf("\n\n当前没有员工记录可以删除!\n"); return; } printf("\n\n当前员工列表: "); for (int i = 0; i < NOE; i++) printf("||%s(ID:%d)|| ", Name[i], ID[i]); printf("\n\n"); int pos; printf("请输入要删除的索引(从0开始,比如第一个员工是0): "); scanf("%d", &pos); // 检查输入的索引是否合法 if (pos < 0 || pos >= NOE) { printf("\n\n输入的索引无效,请输入0到%d之间的数!\n", NOE-1); return; } printf("\n\n正在删除记录...\n"); // 从pos位置开始,将后面的元素向前移动一位 for (int i = pos; i < NOE - 1; i++) { strcpy(Name[i], Name[i + 1]); // 用strcpy真正拷贝字符串 ID[i] = ID[i + 1]; // 同步移动ID数组,保证数据对应 } NOE--; // 员工总数减1 printf("\n\n删除后的员工列表: "); for (int i = 0; i < NOE; i++) printf("||%s(ID:%d)|| ", Name[i], ID[i]); printf("\n\n"); } void Display(){ if (NOE == 0) { printf("\n\n当前没有员工记录可以显示!\n"); return; } printf("\n\n当前员工记录: "); for (int i = 0; i < NOE; i++) printf("||%s %d|| ", Name[i], ID[i]); printf("\n\n"); } int main(){ int Choice; do{ printf("\n1. 注册员工记录\n"); printf("\n2. 删除员工记录\n"); printf("\n3. 显示员工记录\n"); printf("\n4. 退出程序\n"); printf("\n\n请输入你的选择: "); scanf("%d", &Choice); switch(Choice){ case 1: Register(); break; case 2: Delete(); break; case 3: Display(); break; case 4: printf("\n\n正在退出程序...\n\n"); exit(0); default: printf("\n\n无效的选择!\n\n"); } } while(Choice != 4); return 0; }
关键修正点说明
- 用
strcpy实现字符串移动:替换掉原来的判断语句,真正把后面的员工姓名拷贝到前一个位置。 - 同步处理ID数组:移动姓名的同时,把对应的ID也往前移,保证姓名和ID始终一一对应。
- 调整循环条件:改成
i < NOE - 1,避免i+1越界访问数组的无效区域。 - 增加边界检查:判断用户输入的索引是否合法,同时处理没有员工记录的特殊情况,让程序更健壮。
- 提示语优化:明确告诉用户索引是从0开始的,减少输入错误的概率。
这样修改后,你就能准确删除指定位置的员工记录啦!
内容来源于stack exchange
相关产品推荐
相关产品推荐

