软件工程导论个人项目互评

发布时间 2023-09-19 16:13:13作者: HNUXCH

软件工程导论个人项目互评

本博客记录湖南大学2021级软件工程导论个人项目互评与代码分析

成员:

评价人:软件5班 谢昶皓

项目作者:软件5班 杨虎强

需求:

  1. 命令行输入用户名和密码,两者之间用空格隔开(程序预设小学、初中和高中各三个账号,具体见附表),如果用户名和密码都正确,将根据账户类型显示“当前选择为XX出题”,XX为小学、初中和高中三个选项中的一个。否则提示“请输入正确的用户名、密码”,重新输入用户名、密码;
  2. 登录后,系统提示“准备生成XX数学题目,请输入生成题目数量(输入-1将退出当前用户,重新登录):”,XX为小学、初中和高中三个选项中的一个,用户输入所需出的卷子的题目数量,系统默认将根据账号类型进行出题。每道题目的操作数在1-5个之间,操作数取值范围为1-100;
  3. 题目数量的有效输入范围是“10-30”(含10,30,或-1退出登录),程序根据输入的题目数量生成符合小学、初中和高中难度的题目的卷子。同一个老师的卷子中的题目不能与以前的已生成的卷子中的题目重复;
  4. 在登录状态下,如果用户需要切换类型选项,命令行输入“切换为XX”,XX为小学、初中和高中三个选项中的一个,输入项不符合要求时,程序控制台提示“请输入小学、初中和高中三个选项中的一个”;输入正确后,显示“”系统提示“准备生成XX数学题目,请输入生成题目数量”,用户输入所需出的卷子的题目数量,系统新设置的类型进行出题;
  5. 生成的题目将以“年-月-日-时-分-秒.txt”的形式保存,每个账号一个文件夹。每道题目有题号,每题之间空一行;

易错点:

1. 当切换为除小初高以外的选项,出现提示后,即使输入正确信息也无法再切换

2. 切换难度在输入错误后,再输错出现越界异常

3. 生成题目之后,无法退回主页

4. 没有查重功能

代码整体架构:

C:.

│  .gitignore

│  PersonalProjectYHQ.iml

│           

├─MathPaper

│  ├─张三1

│  │      2023-09-18-14-41-09.txt

│  │     

│  └─张三2

│          2023-09-18-14-42-17.txt

│          2023-09-18-14-43-36.txt

│         

├─out

│  └─production

│      └─PersonalProjectYHQ

│          └─yhq

│              ├─entity

│              │      Teacher.class

│              │      User.class

│              │     

│              ├─service

│              │      Data.class

│              │      Log.class

│              │      Main.class

│              │     

│              └─util

│                      FileAndCheck.class

│                      MakePapers.class

│                      WriteJuniorPaper.class

│                      WritePapers.class

│                      WritePrimaryPaper.class

│                      WriteSeniorPaper.class

│                     

└─src

    └─yhq

        ├─entity

        │      Teacher.java

        │      User.java

        │     

        ├─service

        │      Data.java

        │      Log.java

        │      Main.java

        │     

        └─util

                FileAndCheck.java

                MakePapers.java

                WriteJuniorPaper.java

                WritePapers.java

                WritePrimaryPaper.java

                WriteSeniorPaper.java

 

 Data.class:存放用户的账号,密码和初始类型数据

 User.class:接口类,为教师类提供接口

Teacher.class:继承User,包括账号,密码和初始类型三种属性

 Log.class:包括Data属性和Scanner属性,为每一个登录账户提供一个Log对象,完成所有输入操作

FileAndCheck.class:查重类,使用哈希表查重

WritePapers.class:抽象类,可以衍生出三种难度的试卷类

测试流程:

1.登录

选择张三1 123账号(输入非法的账户和密码都会报错并要求重新输入)

图1 登录界面

2.功能选择

输入对应指令会进入对应功能(输入非法指令会报错并要求重新输入)

图2 功能选择

3.选择退出登录

输入-1会退出登录并弹出登录界面,退出登录之后不能再出题以及进行其他操作

图3 退出登录界面

4.选择出题

输入0会进入出题界面,可以选择题目数量,10-30范围之外的数量不可选择

生成后会展示文件存放位置并可以继续操作

图4 出题界面

5.选择切换类型

输入1可以切换小学,初中和高中三种类型,不会出现其他输入BUG

图5 切换界面

6.题目展示

图6 小学,初中和高中习题

总结:

优点:

1.所有的需求都成功实现没有bug;

2.建立了专门的文件夹MathPaper存放各个账户的试卷;

3.代码架构清晰,创建了WritePapers抽象类,三种难度的出卷类继承这个抽象类;

abstract public class WritePapers {//抽象类,可以衍生出三种难度的试卷

  public void paperwriter(int number, File newFile, String NameAndPassword) {
  }
}

 

4.创建了User接口,包括账户,密码和出题类型三个属性,Teacher类继承该接口;

interface User {//用户类接口

  String getTeacher_name();

  void setTeacher_name(String name);

  String getTeacher_password();

  void setTeacher_password(String password);

  String getTeacher_type();

  void setTeacher_type(String type);
}

5.编写方法时使用了throws IOException抛出IO错误,提高代码的性能和可靠性;

6.代码的注释非常完备,可读性很强,功能介绍也很详细;

7.main函数非常的简洁,只需要生成Log对象就可以实现所有功能,可维护性好;

8.所有的输入部分都有清晰的提示语句和错误处理,可以解决所有的输入错误和不规范问题;

9.出的题目逻辑合理,包括括号的嵌套等比较复杂的逻辑,符合难度的需求;

10.使用哈希表存放已有题目并查重。

public boolean Check(File file, String exercise) throws IOException {//Check方法用来实现题目查重功能
    boolean flag = false;//定义flag标志位存储是否重复
    File OldFile = new File(file.getParent());//定义OldFile存储出题文件夹的上一级目录
    File[] OldFileLists = OldFile.listFiles();//获得上一级目录下的所有文件
    if (OldFileLists != null) {//如果有文件
      for (File oldFileList : OldFileLists) {//遍历读取文件夹中的每一个文件
        FileReader fReader = new FileReader(oldFileList);//读取当前文件
        BufferedReader bReader = new BufferedReader(fReader);//读取当前文件中的题目
        while (true) {//遍历读取文件中的每一道题目
          int cnt = 0;//定义计数器读取操作数的数目
          String OldTit = bReader.readLine();//读取当前题目
          if (OldTit == null) {//要求中说明每出一道题则需要空一行,所以遇到空行就需要跳过
            break;
          }
          for (int j = 0; j < OldTit.length(); j++) {//遍历题目每一个字符为了对单个符号数情况进行查重,例如:1+2和2+1为重复
            if (j == '(') {//如果出现括号则证明操作数>1,跳过
              break;
            }
            if (j == '+' || j == '-' || j == '*' || j == '÷') {
              cnt++;//记录符号的数目
            }
          }
          if (cnt == 1) {//如果为单符号数情况
            flag = OneOperanumCheck(OldTit, exercise);
          } else {
            String[] UsedTit = OldTit.split(".");//"1.xxx"从'.'后读取题目字符串
            if (UsedTit.length > 1) {
              if (UsedTit[1].equals(exercise)) {
                flag = true;
              }
            }
          }
        }
      }
    }
    return flag;

 

不足:

1.部分类和方法的命名没有不够规范,没有遵循驼峰命名法

2.题目标号与题干太靠近,容易混杂