结对编程代码互评

结对编程代码互评

本次代码评价基于 lyc 同学的中小学数学卷子自动生成程序(个人项目)进行测试、分析和评价。我和lyc同学一起参加过一些比赛,对彼此的代码风格和处理问题的逻辑都比较熟悉,希望这次能从他的代码中得到新的收获。

代码功能测试

  1. 基础功能分析测试

按照题目给出的用户和常规操作进行测试。

对应的卷子生成在程序所设置的绝对路径下,命名符合题目要求。

生成试卷进一步增加了难度标题,便于用户分辨,优化了用户体验。生成题目的格式符合规范,各个运算符号添加位置合理,符合题目要求。

  1. 随机输入测试

这部分测试不按照题目给出的格式进行,而是随机输入不符合要求的字符测试程序。可以看到,程序在遇到无法识别的字符串时会提示输入错误,并自动返回输入字符串前的状态,由此保障了程序的安全性和高可用性。

综上,可以看出 lyc 同学代码实现的功能和效果还是非常好的。

代码分析

这份代码有四个类:

其中Paper和User是实体类,分别定义了试卷和用户的属性和方法,PaperGenerationSystem是试卷产生系统的工具类,Main是程序的入口。

下面具体分析每个类的实现和作用

User

User类有三个属性:分别是类型,用户名和密码

属性名

类型

含义

type

String

用户此时的生成试卷的类型

username

String

用户名

password

String

密码

构造方法如下

  public User(String type, String username, String password) {
    this.type = type;
    this.username = username;
    this.password = password;
  }

其他方法:

方法名

返回值

作用

getType

String

获取用户类型

setType

void

设置用户类型

getUsername

String

获取用户名

setUsername

void

设置用户名

getPassword

String

获取用户密码

setPassword

void

设置用户密码

总体来说User类设计逻辑清晰,方法得体。

Paper

Paper类有三个属性:分别是三种难度的运算符号

属性名

类型

含义

priSign

String[]

小学试卷操作符号

midSign

String[]

初中试卷操作符号

highSign

String[]

高中试卷操作符号

  private final String[] priSign = {"+", "-", "*", "/"}; // 小学试卷操作符号

  private final String[] midSign = {"²", "√"}; // 初中试卷操作符号

  private final String[] highSign = {"sin", "cos", "tan"}; // 高中试卷操作符号

Paper类只有一个方法,这也是这份代码做的不太好的地方:一个方法过长,即使注释写的比较清楚,也显得繁杂,可读性较低。

方法名

返回值

作用

makeQuestion

String

生成数学题的方法

生成算式的逻辑是按照算式元素从左到右的顺序,除了必须的操作数和加减乘除等于符号,根据试卷类型和随机数来决定是否插入每个符号元素。这种方式生成逻辑清晰,便于理解,但是生成过程繁杂,算法性能并不是很好。

PaperGenerationSystem

PaperGenerationSystem类仅有一个属性,是用户信息的存储链表

属性名

类型

含义

userMessage

List

存储用户信息的链表

PaperGenerationSystem的方法如下:

方法名

返回值

作用

userInit

void

初始化用户信息的链表信息

generate

void

程序的主系统

PaperGeneration

void

试卷生成写入函数

check

boolean

查重函数

isNumeric

boolean

判断是否为数字

  • userInit

使用链表存储小规模的用户信息,避免了数据库的使用,简化了程序。但是在判断登录时,需要遍历链表来比对用户名和密码,效率较低,可以换成hashmap提高查找效率,同时避免用户重复,进而提升程序的工作效率。

 public void userInit() {
    userMessage.add(new User("小学", "张三1", "123"));
    userMessage.add(new User("小学", "张三2", "123"));
    userMessage.add(new User("小学", "张三3", "123"));
    userMessage.add(new User("初中", "李四1", "123"));
    userMessage.add(new User("初中", "李四2", "123"));
    userMessage.add(new User("初中", "李四3", "123"));
    userMessage.add(new User("高中", "王五1", "123"));
    userMessage.add(new User("高中", "王五2", "123"));
    userMessage.add(new User("高中", "王五3", "123"));
  }
  • generate

是程序的主系统,实现了 用户交互部分 的功能,由于代码过长,只展示部分代码。这个方法同样有代码过长的问题,可以进一步封装来提高代码的可读性。

  • 用户登录

    System.out.println("-----欢迎来到中小学数学卷子自动生成系统!-----");
    System.out.println("## 请输入用户名和密码(两者之间用空格隔开)");

    while (true) {
      Scanner sc = new Scanner(System.in);
      String str = sc.nextLine();

      if (!str.contains(" ")) {
        System.out.println("## 输入的账号密码格式不对,请重新输入");
        continue;
      }
  • 难度切换部分

    System.out.println(
            "## 当前选择为"
                + userMessage.get(index).getType()
                + "出题,请输入生成题目数量(题目数量范围为10~30,输入-1将退出当前用户,重新登录),如需切换出题类型,请输入切换为xx,xx为小学、初中和高中三个选项中的一个");
        String command = sc.nextLine();
        if (command.equals("")) {
          System.out.println("请输入内容!");
          continue;
        }
        if (command.equals("切换为小学")) {
          userMessage.get(index).setType("小学");
          continue;
        } else if (command.equals("切换为初中")) {
          userMessage.get(index).setType("初中");
          continue;
        } else if (command.equals("切换为高中")) {
          userMessage.get(index).setType("高中");
          continue;
        }
  • 题目生成部分:根据输入是否有数字和数字的范围,来判断是否要生成题目

    if (isNumeric(command)) {
      if (Integer.valueOf(command) <= 30 && Integer.valueOf(command) >= 10) {
        PaperGeneration(
          Integer.valueOf(command),
          userMessage.get(index).getType(),
          userMessage.get(index).getUsername());
       System.out.println("## 试卷生成成功!请在对应包下查看试卷!");
       } else {
         System.out.println("## 不满足题目数量,请重新输入");
       }
    }
  • PaperGeneration

此方法是 试卷生成写入函数,用于

  1. 新建用户对应的文件夹和txt文件

  1. 将生成的题目经过查重,加序号处理后写入文件

在程序中,文件使用的是绝对路径,因此会在未经过用户同意的情况下,在用户的电脑的对应路径下产生相应的文件夹,可能会造成用户找不到文件的问题,降低用户的使用体验。

由于代码过长,只展示部分代码。这个方法同样有代码过长的问题,可以进一步封装来提高代码的可读性。

  • 获取系统时间

    Date time = new Date();
    SimpleDateFormat df = new SimpleDateFormat("yyyy-MM-dd-HH-mm-ss");
    String title = df.format(time);
  • 生成文件,并将查重后的试题写入文件

    String dirPath = "D:\\IDEA code\\PaperSystem\\system\\src\\com\\papers\\" + username;
    File file = new File(dirPath);

try {
      if (!file.exists()) file.mkdirs();
      String paperDir = dirPath + "\\" + title + ".txt";
      // 写入文件内容,即试题
      File newPaper = new File(paperDir);
      writer = new FileWriter(newPaper);
      // 标明是哪种卷子
      writer.write(type + "期末考试试卷\r\n\r\n");

      int quesIndex = 1; // 题目序号

      // 根据输入的数量开始出题并写入文件
      while (sum > 0) {
        String content = paper.makeQuestion(type);
          // 试题查重
        if (check(newPaper, content)) {
          if (sum == 1) {
            writer.write(quesIndex + ". " + content);
            break;
          }
          writer.write(quesIndex + ". " + content + "\r\n" + "\r\n");
          sum--;
          quesIndex++;
        }
        if (!check(newPaper, content)) {
          System.out.println(content);
        }
      }
     // 刷新并关闭FileWriter 
      writer.flush();
      writer.close();
    } catch (IOException e) {
      e.printStackTrace();
    }
  • check

此方法负责对题目进行查重,主要思路是遍历用户文件夹下的txt文件,逐个对比题目是否重复。这部分有一个小缺陷

      // 只有一张卷子不查重
      if (files.length == 1) {
        return true;
      }

我认为在同一张卷子的生成过程中,题目仍需与上面已经生产的题目进行查重处理。

  • isNumeric

此方法的作用是判断输入的字符串是否是数字,如果是数字则可能可以进行题目生成处理。

  public boolean isNumeric(String str) {
    Pattern pattern = Pattern.compile("[0-9]*");
    Matcher isNum = pattern.matcher(str);
    if (!isNum.matches()) {
      return false;
    }
    return true;
  }

代码评价

  • 优点:

  1. 这份代码的功能实现十分完备,各个判断和边界考虑的清晰周到。

  1. 类的设计逻辑清晰,易于他人理解。

  1. 程序的文字提示十分完善,便于用户操作。

  1. 属性的安全性较好,在适当的地方采用了private和final关键字进行处理。

  • 缺点:

  1. 方法的封装不够完善,程序整体的可读性偏差。

  1. 存储用户信息用的是链表,查找效率较低,可以采用map或者数据库

  1. 文件生成的路径是绝对路径,单从终端无法得知文件生成在哪里。

  1. 算法相对较为简单,效率较低,期待可以进行优化。

总体上来说,lyc同学编写的程序还是很值得我去学习的,尤其是在用户体验方面的考虑十分周到,向yc大佬低头!

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值