2016012053小学四则运算练习软件项目报告

时间:2023-02-14 13:11:41

Coding.net源码仓库地址:https://git.coding.net/ma744191948/mayue.git

 

一、需求分析

1、用JAVA编程语言写一个小学四则运算练习

2、程序可接收一个输入参数n,随机生成N道小学四则运算题

3、每个数字在0~100之间,运算符在3个~5个之间。

4、每个练习至少包含两种运算符,运算符为+-*÷

5、题目中不能出现负数和正整数

6、要将学号和n道练习题以及答案输出到文件“result.txt”中

 

二、功能设计

基本功能:根据用户需要用java编程语言写一个四则运算,数字在100以内,运算符3个到5个之间,每个练习至少包含两种运算符,运算符为+-*÷,且题目中不能出现负数和正整数,然后式子和答案以文档的形式呈现在用户面前。

拓展功能:支持有括号的运算

 

三、设计实现

我共设计了四个类:Main、Demo1、Demo2、ToolDemo

Main:主类,将学号、练习题以及答案输入到文件“result.txt”文件中

Demo1:输出表达式,对表达式的条件进行判断,对表达式进行验证

Demo2:判断左右子树是否有孩子,判断随机产生的符号以及是否有括号的运算。

ToolDemo:获取随机的四种符号和0~100的随机数。

 

四、算法详解

1.生成题目
(1)随机获取运算符
char sign = 0;
        Random num = new Random();
        int i = num.nextInt(4);
        switch (i) {
        case 0:
            sign = '+';
            break;
        case 1:
            sign = '-';
            break;
        case 2:
            sign = '*';
            break;
        case 3:
            sign = '/';
            break;
        }
        return sign;
(2)根据输入的范围(0-100)获取随机数
int number = 0;
        Random num = new Random();
        number = num.nextInt(max + 1);
        return number;
2.获取表达式验证并计算结果
获取每个节点的运算结果,并检验除法
     1)除数为0
     2)不能整除
     出现以上两种情况的话将该运算符转换成其他三种运算符
public String toString(){
            String str = root.toString();
            str = str.substring(1, str.length()-1);
            return str;
        }

3.结果写入
使用BufferedWriter写入文本
File file = new File("result.txt");
        try {
            BufferedWriter bw = new BufferedWriter(new FileWriter(file, true));
            bw.write("学号:2016012053" + "\r\n");
            for (int i = 0; i < n; i++) {
                Integer number = null;
                Random num = new Random();
                number = num.nextInt(3) + 2;
                bTree = new YunsuanVo(number);
                bTree.buildBTree();
                String result = bTree.CalAndVal();
                System.out.println(bTree.toString() + "=" + result);
                bw.write(bTree.toString() + "=" + result + "\r\n");
            }
            System.out.println("---------------------------");
            bw.close();
        } catch (IOException e) {
            e.printStackTrace();
        }
        

    }

五:测试运行

2016012053小学四则运算练习软件项目报告

 

 2016012053小学四则运算练习软件项目报告

后来改进后的命令行输入为

2016012053小学四则运算练习软件项目报告

 

2016012053小学四则运算练习软件项目报告

 

六、优秀代码展示

 

public class Main {
    public static void main(String[] args) {

        Scanner scan = new Scanner(System.in);
        int n;
        System.out.println("请输入您想要得到的题目个数:\n");
        n = scan.nextInt();
        Demo1 bTree;
        System.out.println("\n");
        System.out.println("2016012053");
        System.out.println("---------------------------");

        File file = new File("result.txt");
        try {
            BufferedWriter bw = new BufferedWriter(new FileWriter(file, true));
            bw.write("2016012053" + "\r\n");
            for (int i = 0; i < n; i++) {
                bTree = new Demo1(2);
                bTree.buildBTree();
                String result = bTree.Verification();
                System.out.println(bTree.toString() + "=" + result);
                bw.write(bTree.toString() + "=" + result + "\r\n");
            }//把输出结果写入到result.txt文件中
            System.out.println("---------------------------");
            bw.close();
        } catch (IOException e) {
            e.printStackTrace();
        }
        

    }

}
/**
     * 生成二叉树
     * 
     */
    public void buildBTree() {
        Demo2 lchild, rchild, lnode, rnode;

        if (num == 1) {
            lchild = new Demo2(String.valueOf(ToolDemo.getNumber(10)), null, null);
            rchild = new Demo2(String.valueOf(ToolDemo.getNumber(10)), null, null);
            root = new Demo2(String.valueOf(ToolDemo.getSign()), lchild, rchild);
        } else {
            int num1 = 0;
            int n = getDeep() - 3;
            boolean[] place = ToolDemo.getChildPlace(num);
            root = new Demo2(String.valueOf(ToolDemo.getSign()), null, null);
            opeList.add(root);

            for (int i = 0; i < n; i++) {
                for (int j = 0; j < (int) Math.pow(2, i); j++, num1++) {
                    lchild = new Demo2(String.valueOf(ToolDemo.getSign()), null, null);
                    rchild = new Demo2(String.valueOf(ToolDemo.getSign()), null, null);
                    opeList.get(j + num1).setChild(lchild, rchild);
                    opeList.add(lchild);
                    opeList.add(rchild);
                }
            }

            for (int i = 0; i < place.length; i++) {
                if (place[i]) {
                    lnode = new Demo2(String.valueOf(ToolDemo.getNumber(10)), null, null);
                    rnode = new Demo2(String.valueOf(ToolDemo.getNumber(10)), null, null);
                    if (i % 2 == 0) {
                        lchild = new Demo2(String.valueOf(ToolDemo.getSign()), lnode, rnode);
                        opeList.add(lchild);
                        opeList.get(num1).setLchild(lchild);
                    } else {
                        rchild = new Demo2(String.valueOf(ToolDemo.getSign()), lnode, rnode);
                        opeList.add(rchild);
                        opeList.get(num1).setRchild(rchild);
                    }
                } else {
                    if (i % 2 == 0) {
                        lchild = new Demo2(String.valueOf(ToolDemo.getNumber(10)), null, null);
                        opeList.get(num1).setLchild(lchild);
                    } else {

                        rchild = new Demo2(String.valueOf(ToolDemo.getNumber(10)), null, null);
                        opeList.get(num1).setRchild(rchild);
                    }
                }
                num1 = num1 + i % 2;
            }
        }
    }

}
/**
     * 获取每个节点的运算结果
     * 
     * @return result
     */
    public String getResult() {
        if (hasChild()) {
            switch (str) {
            case "+":
                return String.valueOf(Integer.parseInt(getLchild().getResult()) + Integer.parseInt(getRchild().getResult()));
            case "-":
                if (Integer.parseInt(getLchild().getResult()) - Integer.parseInt(getRchild().getResult()) < 0) {
                    while (str.equals("-")) {
                        str = String.valueOf(ToolDemo.getSign());
                    }
                    return this.getResult();
                } else {
                    return String.valueOf(Integer.parseInt(getLchild().getResult()) - Integer.parseInt(getRchild().getResult()));
                }
            case "*":
                return String.valueOf(Integer.parseInt(getLchild().getResult()) * Integer.parseInt(getRchild().getResult()));
            case "/":
                if (getRchild().getResult().equals("0")) {
                    while (str.equals("/")) {
                        str = String.valueOf(ToolDemo.getSign());
                    }
                    return this.getResult();
                } else if (Integer.parseInt(getLchild().getResult()) % Integer.parseInt(getRchild().getResult()) != 0) {
                    while (str.equals("/")) {
                        str = String.valueOf(ToolDemo.getSign());
                    }
                    return this.getResult();
                } else
                    return String.valueOf(Integer.parseInt(getLchild().getResult()) / Integer.parseInt(getRchild().getResult()));
            }
        }
        return str;
    }
/**
     * 根据输入的范围获取随机数
     * 
     * @param max
     * @return number
     */
    public static int getNumber(int max) {
        int number = 0;
        Random num = new Random();
        number = num.nextInt(max + 1);
        return number;
    }

    /**
     * 随机产生子节点
     * 
     * @param num
     * @return childPlace
     */

    public static boolean[] getChildPlace(int num) {
        int d = 0;
        int size = 0, j = 1;
        while (num >= (int) Math.pow(2, j)) {
            j++;
        }
        d = (int) Math.pow(2, j) - 1 - num;
        size = (int) Math.pow(2, j - 1);
        boolean[] k = new boolean[size];
        for (int i = 0; i < size; i++) {
            k[i] = true;
        }
        for (int i = 0; i < d; i++) {
            Random ran = new Random();
            int f = ran.nextInt(size);
            while (k[f] == false) {
                f = ran.nextInt(size);
            }
            k[f] = false;
        }
        return k;
    }

    
    

}

 

七、PSP

PSP2.1

任务内容

计划共完成需要的时间(min)

实际完成需要的时间(min)

Planning

计划

1500

7200

·        Estimate

·   估计这个任务需要多少时间,并规划大致工作步骤

1500

7200

Development

开发

1300

6000

·        Analysis

·         需求分析 (包括学习新技术)

30 300

·        Design Spec

·         生成设计文档

30

300

·        Design Review

·         设计复审 (和同事审核设计文档)

30

300

·        Coding Standard

·         代码规范 (为目前的开发制定合适的规范)

20

400

·        Design

·         具体设计

50

500

·        Coding

·         具体编码

800

3000

·        Code Review

·         代码复审

30

500

·        Test

·         测试(自我测试,修改代码,提交修改)

200

1000

Reporting

报告

200

1200

·         Test Report

·         测试报告

70

400

·         Size Measurement

·         计算工作量

60

200

·         Postmortem & Process Improvement Plan

·         事后总结, 并提出过程改进计划

70

600

 

八、总结

       这次项目比我想象中的要难很多,如果说用c语言来写就会简单很多,而Java编程语言相对我来说难很多,也比预想中做的时间长了很多很多,原本觉得自己一两天就可以完成,但实际是一个星期每天都有再弄这个项目,考虑这个项目应该如何实现,代码应该如何写?以前觉得算法并没有什么太大的用处,也觉得自己可能不会去学算法之类的东西,但做完这个项目之后就发现,算法实在是太重要了。经过这一个星期,我明白了自己在Java方面还有很多很多不足的地方,在算法和思维方面也有很多不足,在接下来的学习生活中,我应该更加努力地去学习,让自己一天比一天更优秀。