BUAA-OO-第四单元总结
正向建模与开发
正向建模是指在软件系统开发的早期阶段,基于需求和设计文档等资料,使用建模工具进行系统的设计和建模,根据需求、设计和代码之间的关系来构建模型和图形化展示系统结构和行为。本单元要求先对系统进行正向建模画出uml图后在进行代码的具体编写及开发。但是在具体实践过程中,一开始我对代码的逻辑不够清晰,所以我是先编写代码后再画uml类图。
架构设计
整体架构如下:
本单元作业要求模拟一个图书馆的功能,包含借书处、预约处、学生、书架等实体。因此我分别为借书处、预约处、学生、书架建立类,同时还写了manager类,用于处理图书的整理过程。
借书处需要处理用户的借书、续借、还书行为。预约处处理用于预约行为。bookshelf用于记录系统中各书的数量及位置。在第三次作业中,添加了pdcplace用于处理图书的捐献。在输入指令时,根据指令的类型,调用不同类的处理函数进行处理。代码如下:
while (true) {
LibraryCommand command = LibrarySystem.SCANNER.nextCommand();
if (command == null) {
break;
}
LocalDate date = command.getDate();
if (command instanceof LibraryOpenCmd) {
// 在图书馆开门之前干点什么
manager.dealOpen(command);
} else if (command instanceof LibraryCloseCmd) {
// 在图书馆关门之后干点什么
manager.dealClose(command);
} else if (command instanceof LibraryQcsCmd) {
// manager.dealCredit(command);
if (!allstudent.containsStudent(((LibraryQcsCmd) command).getStudentId())) {
student student = new student(((LibraryQcsCmd) command).getStudentId());
allstudent.addstudent(((LibraryQcsCmd) command).getStudentId(), student);
}
String studentid = ((LibraryQcsCmd) command).getStudentId();
int credit = allstudent.getstudent(studentid).getCredit();
LibrarySystem.PRINTER.info(date, studentid, credit);
} else {
// LibraryRequest request = (LibraryRequest) command.getCmd();
LibraryReqCmd req = (LibraryReqCmd) command;
// 对 request 干点什么
if (req.getType() == LibraryRequest.Type.BORROWED) {
if (!allstudent.containsStudent(req.getStudentId())) {
student student = new student(req.getStudentId());
allstudent.addstudent(req.getStudentId(), student);
}
borrowplace.dealborrow(allstudent.getstudent(req.getStudentId()), command);
} else if (req.getType() == LibraryRequest.Type.ORDERED) {
//request.getStudentId() order request.getbookId()
if (!allstudent.containsStudent(req.getStudentId())) {
student student = new student(req.getStudentId());
allstudent.addstudent(req.getStudentId(), student);
}
orderplace.dealOrder(allstudent.getstudent(req.getStudentId()), command);
} else if (req.getType() == LibraryRequest.Type.PICKED) {
orderplace.dealPick(allstudent.getstudent(req.getStudentId()), command);
} else if (req.getType() == LibraryRequest.Type.QUERIED) {
LibraryBookId libraryBookId = req.getBookId();
if (libraryBookId.isFormal()) {
bookshelf.query(req.getBookId(), command);
} else if (!libraryBookId.isFormal()) {
pdcPlace.query(libraryBookId, command);
}
} else if (req.getType() == LibraryRequest.Type.RETURNED) {
borrowplace.dealreturn(allstudent.getstudent(req.getStudentId()), command);
} else if (req.getType() == LibraryRequest.Type.DONATED) {
if (!allstudent.containsStudent(req.getStudentId())) {
student student = new student(req.getStudentId());
allstudent.addstudent(req.getStudentId(), student);
}
pdcPlace.dealDonate(allstudent.getstudent(req.getStudentId()), command);
} else if (req.getType() == LibraryRequest.Type.RENEWED) {
orderplace.dealRenew(allstudent.getstudent(req.getStudentId()), command);
}
}
// bookshelf.size();
}
四个单元中架构设计思维的演进
第一单元
第一单元的主题是表达式解析。本单元中采用递归下降方法进行解析。因此程序整体架构比较明确。需要考虑较多的是增加功能的封装。通过借鉴公众号中推送的代码及实验课的代码,我逐步完成了第一次作业。
第二单元
第二单元的主题是电梯调度,电梯调度使用多线程实现。由于本单元是第一次结束java的多线程编程,而多线程程序编写的时候会产生各程序之间的竞争问题,可能出现死锁。因此在架构设计时需要考虑各线程对临界资源的访问顺序,对架构进行优化。此外,第二单元主要学习了生产者-消费者架构。
第三单元
第三单元的主题是JML约束。第三单元要求我们按照指定的规格完成相应代码的编写。具体来说,规格指定了类中每一个方法的前序条件及后序条件,也就是说,在保证前序条件满足的情况下后序条件一定实现。本单元中,代码的整体架构已被JML约束。我们可以改变的是存储关系图的数据结构或搜索算法等。
第四单元
第四单元的主题是UML及图书管理系统。第四单元要求使用UML模块设计思想进行系统的正向建模,构建类图、状态图和顺序图来构建自己的架构,保证开发之中的高内聚低耦合的要求。
测试思维的演进
第一单元主要对一些极端数据进行测试。第二单元的测试对于电梯死锁、轮询等问题进行测试。由于多线程及调度的不确定性,不同代码的输出基本不可能一样,但是需要保证程序无死锁轮询。第三单元测试思想是黑箱测试和白箱测试相结合。本单元主要测试代码的复杂度,防止出现TLE现象。第四单元主要是交互测试,本单元对于性能要求并没有那么高。
感想
1.通过本次课程的学习,我提高了自己的编码能力,更加了解了面向对象的思想,以及黑盒测试、白盒测试等等。
2.与第一点对应的,OO课程的强度和编码难度对我是一个巨大的挑战…