从零开始学Java:第35章 综合项目需求分析:命令行学习管理系统 第35章 综合项目需求分析命令行学习管理系统前面五个阶段已经学了 Java 基础、面向对象、集合、文件、异常、测试、并发、HTTP、数据库和 JVM。第六阶段不再单独讲一个知识点而是从一个完整项目出发把这些能力串起来。项目名称命令行学习管理系统。它不是大型在线教育平台而是一个适合 Java 基础阶段收尾的综合项目。我们用命令行交互用文件保存数据用清晰分层组织代码用测试验证核心业务。这一章先不急着写代码。真实项目的第一步不是打开 IDE而是把需求说清楚。一、项目目标系统要支持管理用户。管理课程。用户报名课程。查询用户已报名课程。查询课程报名人数。保存数据到文件。程序重启后恢复数据。用户可以理解为学习者。课程可以理解为教程、训练营、视频课。报名关系表示某个用户选了某门课。二、为什么选择这个项目这个项目适合作为 Java 基础综合练习因为它包含对象建模User、Course、Enrollment。集合Map、List、Set。文件CSV 保存和读取。异常重复报名、用户不存在、课程不存在。项目结构model、service、store、app。测试业务规则很适合写单元测试。后续扩展可以改数据库、HTTP、图形界面。它的业务不复杂但足够训练工程思维。三、角色和实体核心实体User 用户 Course 课程 Enrollment 报名记录关系UseruserIdnameemailactiveCoursecourseIdtitleteachercapacityactiveEnrollmentenrollmentIdusercourseenrolledAtcancelled为什么要有Enrollment因为报名不是简单把课程放进用户列表。报名本身有信息谁报名。报了哪门课。什么时候报名。是否取消。所以它应该成为独立对象。四、功能清单第一版功能1. 注册用户 2. 添加课程 3. 用户报名课程 4. 取消报名 5. 查询所有用户 6. 查询所有课程 7. 查询某个用户已报名课程 8. 查询某门课程报名用户 9. 保存数据 0. 退出不要一开始就做登录、权限、支付、视频播放、Web 页面。项目初期要控制范围。五、业务规则用户规则用户 ID 不能为空。用户名不能为空。邮箱可以为空。用户 ID 唯一。停用用户不能报名。课程规则课程 ID 不能为空。课程标题不能为空。老师可以为空。容量必须大于 0。课程 ID 唯一。停用课程不能报名。报名规则用户必须存在。课程必须存在。用户不能重复报名同一门未取消课程。课程人数不能超过容量。取消不存在的报名要失败。已取消的报名不能重复取消。这些规则后面都要写进 Service并通过测试验证。六、数据存储设计第一版用 CSV 文件data/users.csv data/courses.csv data/enrollments.csv用户userId,name,email,active U001,小林,linexample.com,true课程courseId,title,teacher,capacity,active C001,Java基础,李老师,30,true报名enrollmentId,userId,courseId,enrolledAt,cancelled E001,U001,C001,2026-06-23,false读取顺序先读 users 再读 courses 最后读 enrollments因为报名记录要根据 userId 和 courseId 找回对象引用。七、项目分层设计app LearningApp CommandLoop model User Course Enrollment service LearningService store UserCsvStore CourseCsvStore EnrollmentCsvStore LearningDataStore util Csv CsvParser DateFormats exception LearningException职责model对象和自身规则。service跨对象业务流程。store文件保存和加载。app命令行交互。util通用工具。exception业务异常。八、核心流程报名课程否是否是是否是否输入 userId/courseId查找用户用户存在且启用?抛出错误查找课程课程存在且启用?抛出错误是否重复报名?抛出错误课程是否已满?抛出错误创建Enrollment保存记录这个流程适合放在LearningService.enroll(userId, courseId)。不要把这些判断写在命令行菜单里。九、核心查询查询某个用户已报名课程遍历 enrollments 筛选 userId 相同 筛选未取消 取 course 返回 ListCourse查询课程报名用户遍历 enrollments 筛选 courseId 相同 筛选未取消 取 user 返回 ListUser这两个查询可以用普通循环也可以用 Stream。初学项目建议先用普通循环写清楚再用 Stream 重构。十、异常策略业务错误thrownewLearningException(用户不存在userId);存储错误thrownewStorageException(保存用户文件失败,e);命令行入口统一捕获try{service.enroll(userId,courseId);dataStore.save(service);System.out.println(报名成功);}catch(RuntimeExceptione){System.out.println(操作失败e.getMessage());}不要在底层到处System.out.println。底层抛异常上层决定怎么提示。十一、测试计划至少测试注册用户成功。重复用户失败。添加课程成功。课程容量必须大于 0。用户报名课程成功。用户重复报名失败。课程满员后报名失败。取消报名成功。重复取消失败。查询用户课程正确。查询课程用户正确。CSV 保存和加载正确。测试计划先写出来后面实现时就不会只测正常流程。十二、第一版不做什么明确不做登录密码。管理员权限。Web 页面。数据库。HTTP 接口。多线程报名。支付。视频播放。这些以后都能扩展但第一版不要贪。项目失败往往不是因为功能太少而是一开始范围太大。十三、迭代计划第一步实现 model。第二步实现 service 内存版。第三步给 service 写测试。第四步实现 CSV store。第五步实现命令行菜单。第六步启动加载、操作后保存。第七步补充错误处理和边界测试。这个顺序很重要。不要一开始就写菜单。菜单最容易让你把业务逻辑写散。十四、练习画出 User、Course、Enrollment 的类图。写出报名课程的完整业务规则。设计 users.csv、courses.csv、enrollments.csv 表头。列出至少 10 个测试用例。思考如果课程容量从 30 改成 50会影响哪些类。十五、本章小结你现在完成了综合项目的需求分析。你应该明确项目不是先写代码而是先定边界。实体来自业务名词但要判断它有没有独立状态和规则。报名关系应该建模成 Enrollment。CSV 文件保存的是 ID不是对象引用。Service 负责业务流程。Store 负责存储。App 负责交互。第一版要控制范围后续再扩展。下一章开始搭建项目结构并写出第一批核心类。