211606356 陈宇 211606333温志铭

三年级学生的轻松代码

一、预估与实际

PSP2.1 Personal Software Process Stages 预估耗时(分钟) 实际耗时(分钟)
Planning 计划 950 1260
• Estimate • 估计这个任务需要多少时间 30 30
Development 开发 60 80
• Analysis • 需求分析 (包括学习新技术) 120 180
• Design Spec • 生成设计文档 30 45
• Design Review • 设计复审 10 15
• Coding Standard • 代码规范 (为目前的开发制定合适的规范) 30 30
• Design • 具体设计 40 60
• Coding • 具体编码 300 500
• Code Review • 代码复审 50 60
• Test • 测试(自我测试,修改代码,提交修改) 60 60
Reporting 报告 70 90
• Test Repor • 测试报告 30 50
• Size Measurement • 计算工作量 30 30
• Postmortem & Process Improvement Plan • 事后总结, 并提出过程改进计划 30 30
合计 1260

二、需求分析

我通过百度的方式了解到,小学三年级数学有如下的几个特点:

  • 特点1:算式拥有多个运算符

  • 特点2:算式包含括号

  • 特点3:答案不能有余数

  • 特点4:除数不能为0

经过分析,我认为,这个程序应当:

  • 要让题目包含随机运算符个数和符号
  • 要有随机的括号,让学生明白括号的优先级比乘除大
  • 答案不存在余数
  • 数字要大于0
  • 除数不能为0

三、设计

1. 设计思路

  • 这个程序需要在之前一二年级的基础上,增加一个三年级的出题方法
  • 主类的作用是通过用户输入-n+数字 -grade+数字从而来判断要调用哪个方法来运行
  • gradeThreee()这个方法需要先判断随机的运算符个数和运算符类型,再通过各种限制来实现加括号的功能
  • 算式出来之后要运用逆波兰方法来实现算式的计算,从而得出答案

2. 实现方案

  • 先有args[]长度判断用户输入的数据如不输入则默认输出100道3年级题名

  • 通过gradeThree()方法生成三年级算式

  • 通过网上查找学习逆波兰运算规则,用来求出算式答案

  • 逆波兰参考网站:https://www.cnblogs.com/chensongxian/p/7059802.html
    这是类图

这是逆波兰说明图

四、编码

1. 调试日志

  • 添加括号时出现(a+(b)+c)*d的情况,我添加了一个int数组flag标记括号的情况,默认为1,1为该数字有左括号,2右括号,只有为 0,1能添加左括号,1,2能添加右括号。

2. 关键代码

String[] str2 = new String[n1 + 1];
int[] flag = new int[n1 + 1];// 标记数组0(,1无符号,2)
for (int j = 0; j < n1 + 1; j++) {
flag[j] = 1; }
int front = -2; String ss = null;// 用来保存一个算式,让它先为一个数字
for (int x = 0; x < n1; x++) {
if (fuhao1[x].equals("+") || fuhao1[x].equals("-")) {
int n2 = (int) (0 + Math.random() * (2 - 1 + 1));// 随机生成0或1,用来随机生成加减法的括号
boolean tag = false;// 用来标记是否括号成队
if (n2 == 0) {
if (front == x - 1) {//如果前一个符号周围有括号
if ((flag[x - 1] == 1 || flag[x - 1] == 0) && flag[x - 1] != 2 && !tag) {
str2[x - 1] = "(" + str2[x - 1];
flag[x - 1] = 0;
} else {
tag = true;
}
if ((flag[x + 1] == 1 || flag[x + 1] == 2) && flag[x + 1] != 0 && !tag) {
str2[x + 1] = str2[x + 1] + ")";
flag[x + 1] = 2;
} else {
tag = true;
}
} else {
if ((flag[x] == 1 || flag[x] == 0) && flag[x] != 2 && !tag) {
str2[x] = "(" + str2[x];
flag[x] = 0;
} else {
tag = true;
}
if ((flag[x + 1] == 1 || flag[x + 1] == 2) && flag[x + 1] != 0 && !tag) {
str2[x + 1] = str2[x + 1] + ")";
flag[x + 1] = 2;
} else {
tag = true;
}
front = x;// 标记当前符号位置
}
}
}

3. 代码规范

  • 代码中的命名均不能以下划线或美元符号开始,也不能以下划线或美元符号结束。
  • 不允许任何未经定义的常量直接出现在代码中
  • 在 if/else/for/while/do 语句中必须使用大括号。 即使只有一行代码,避免使用单行的形式

五、测试

  • 输入参数-n 18.5 -grade 2 时 输出:请输入正数 !符合预期
  • 输入参数-n 18 -grade 2.5时 输出:请输入正数 ! 符合预期
  • 输入参数-n 18 时 输出:您输入的参数有误,请重新运行 ! 符合预期
  • 输入参数-grade 2时 输出:您输入的参数有误,请重新运行 !!符合预期
  • 输入参数-n 18 -grade 4时 输出:目前只支持1-3年级,请重新输入!符合预期

六、总结

请总结过程中的教训和经验,思考

  • 这次做作业的过程中,了解了逆波兰算法,和调度场算法,明白了自己对栈的理解不够和数据结构的生疏,以后应该加强这方面的知识
  • 学会了查看队友的代码,出现错误时如何复现过程如何debug