
本文讲解如何使用java实现学生信息的重复录入与统一打印,通过正确管理数组索引、循环控制和输入处理,解决用户在多次添加数据后无法保存或显示全部记录的问题。
本文讲解如何使用java实现学生信息的重复录入与统一打印,通过正确管理数组索引、循环控制和输入处理,解决用户在多次添加数据后无法保存或显示全部记录的问题。
在开发学生信息管理系统时,一个常见需求是:允许用户连续录入多条学生记录(ID、姓名、学院、专业),并在输入“no”后一次性打印所有已录入的数据。但初学者常因变量作用域错误、索引未递增、循环嵌套失当等问题导致仅能保存最后一条数据,或程序陷入死循环。下面将给出结构清晰、健壮可靠的解决方案。
✅ 核心问题分析与修正要点
原代码存在三个关键缺陷:
- row 变量在每次循环内被重置为 0,导致新数据总覆盖首行;
- case "yes" 中未更新 row,致使后续录入仍写入同一行;
- case "no" 仅打印最后一行(students[row][...]),且未遍历全部有效记录;
- 内层 while(in.hasNext()) 无实际必要,反而干扰流程控制。
✅ 推荐实现方案(优化版)
import java.util.Scanner;
public class StudentInfoManager {
public static void main(String[] args) {
// 使用二维数组存储最多50名学生,每名学生4项信息
String[][] students = new String[50][4];
Scanner in = new Scanner(System.in);
int row = 0; // 全局计数器:指向下一个空闲行,初始化在循环外!
System.out.println("=== 学生信息录入系统 ===");
while (true) {
System.out.println("\n--- 录入第 " + (row + 1) + " 位学生 ---");
System.out.print("请输入学号: ");
students[row][0] = in.nextLine().trim();
System.out.print("请输入姓名: ");
students[row][1] = in.nextLine().trim();
System.out.print("请输入学院: ");
students[row][2] = in.nextLine().trim();
System.out.print("请输入专业: ");
students[row][3] = in.nextLine().trim();
System.out.println("✅ 记录已保存!");
// 询问是否继续
String decision;
do {
System.out.print("是否继续添加?(YES/NO): ");
decision = in.nextLine().trim().toLowerCase();
if (!decision.equals("yes") && !decision.equals("no")) {
System.out.println("⚠️ 请输入 'YES' 或 'NO'(不区分大小写)");
}
} while (!decision.equals("yes") && !decision.equals("no"));
if ("yes".equals(decision)) {
row++; // ✅ 关键:成功录入后才递增索引
if (row >= students.length) {
System.out.println("⚠️ 学生列表已满(最大50人),停止录入。");
break;
}
} else {
break; // 输入"no",退出录入循环
}
}
// 批量打印全部有效记录
System.out.println("\n" + "=".repeat(60));
System.out.printf("%-12s %-20s %-15s %-15s%n",
"学号", "姓名", "学院", "专业");
System.out.println("-".repeat(60));
for (int i = 0; i <= row; i++) {
if (students[i][0] != null) { // 防空指针(确保该行有数据)
System.out.printf("%-12s %-20s %-15s %-15s%n",
students[i][0],
students[i][1] != null ? students[i][1].toUpperCase() : "",
students[i][2] != null ? students[i][2].toUpperCase() : "",
students[i][3] != null ? students[i][3].toUpperCase() : "");
}
}
System.out.println("=".repeat(60));
System.out.println("共录入 " + (row + 1) + " 条学生信息。");
}
}? 关键改进说明
- 索引管理:row 定义在 while 外部,并仅在确认添加成功后执行 row++,确保每条记录写入独立行;
- 输入鲁棒性:使用 trim() 去除首尾空格,toLowerCase() 统一判断,配合 do-while 循环强制用户输入合法值;
- 安全打印:遍历 0 到 row(含),并检查 students[i][0] != null 避免打印未初始化行;
- 格式化输出:采用 printf 实现对齐排版,提升可读性;学院与专业名称转大写符合常规展示需求;
- 边界防护:当 row 达到数组上限时主动终止,防止 ArrayIndexOutOfBoundsException。
⚠️ 注意事项
- 若需长期存储或处理大量数据,应改用 ArrayList
封装对象(推荐定义 Student 类),避免硬编码二维数组的局限性; - 生产环境中建议加入学号唯一性校验、输入非空验证等业务逻辑;
- Scanner 在读取 nextLine() 前若存在 nextInt() 等遗留换行符,需调用一次 in.nextLine() 清理缓冲区——本例未涉及数字输入,故无需处理。
通过以上重构,程序逻辑清晰、容错性强,真正实现了“边录边存、统一输出”的核心目标,是Java基础输入输出与循环控制的典型实践范例。










