第一次作业-四则运算题目生成程序
代码仓库:https://git.coding.net/EtihwXD/Quiz.git
需求分析:
- 能够指定生成数的范围,生成题目的数量和存放题目的文件
- 生成题目时应当计算出结果并保存到文件中,且结果应为真分数
- 给定一个存放题目的文件和一个存放答案的文件,能够判断出正确和错误的题数,指出正确/错误题目的序号,且指出已有题目中重复的部分。最后结果存入文件中。
- 随机产生括号
功能设计:
- 应对输入参数的合法性进行校验
- 用户未指定时,提供默认的生成题目数和存放文件名
- 一道题的运算符不应超过三个
- 括号的分布应该合法且合理,如类似(a+b+c)的括号不应该存在
设计实现:
整个程序的逻辑主要分布在4个文件中:
Quiz.cpp : 用int argc, char* argv[]来判断输入参数的合法性,并根据输入参数的不同,进入不同的分支。
setQuiz.h : 存放生成题目所需函数的头文件。该头文件包含获取整数/真分数,获取运算符和生成数学表达式并存入文件这三个函数。
duplicate.h : 存放题目查重功能的函数的头文件,查重功能后文描述
calculate.h : 存放计算表达式的函数的头文件。该头文件包含计算运算符优先级、求最大公约数、求最小公倍数、中缀表达式转换为后缀表达式和计算后缀表达式这五个函数。
中缀表达式转换为后缀表达式时,因为题目中真分数的存储形式为(a'b/c),除法的存储方式为a÷b。所以遇到真分数时,把真分数转化为 (a*c+b)/c的形式再转换;当遇到a÷b的情况时,因为÷在string中占2位,所以遇到÷就把/号存入string中并将计数器移后一位。
查重功能:实现查重功能时,我参考了哈希表的思想,构建了哈希表的表头,将题目结果的第一个整数(题目结果可能是分数,所以只取第一个整数)对10取模,分存在哈希表表头的大小为10的数组里。表头的数组中的每一位都存储着一个链表,链表的结点中存储着题目的运算符、操作数和结果,并且这些数据已经通过排序算法排序。 每次需要查重时,就会调用查重算法,去表中寻找结果、操作数和运算符与当前式子都相同的节点,若这样的节点存在,就说明这个题目之前已经出现过。
测试运行:
所有参数齐全时,输出在控制台中,并且生成两个文件
输入参数不合法时输出
文件比对功能,结果输入Grade.txt文件(题目文件经过修改,并非用生成文件进行比对)
一次生成10000条题目
个人软件过程:
|
小结:
通过这次的作业,我深刻地认识到自己水平实在是太低了。开发这个程序的时候,我用的是c的语法,但使用了很多c++的函数,很多功能都是一边查一边学一边写的。这个程序的开发过程可以说是磕磕绊绊,对每一个功能,我先把思路画到纸上进行分析,但在实际开发的时候总能遇到这样那样的问题,无数次地修改实现方法,甚至偶尔会推翻重来。可能是我的水平太低了,我在图书馆从14:30做到21:30也才完成了一个功能模块的开发和测试,和周围的同学相比实在是太慢了,但好在成功地在最后期限前完成了这个程序,这个程序的代码有1100多行,非常繁杂。
在开发过程中,因为使用同样的语言,我和郭达(@daleag)进行了许多次的交流,在很多问题上都得出了解决方案。我在交流中学到了很多解决问题的思路,这让我受益良多。
在测试的时候,bug总是一个接一个地来,一段程序总是要修修补补才能真正发挥作用,一开始想到的思路常常是错漏百出的。以后考虑问题一定要仔细、周全一些,如果可以的话更应该多和其他同学交流,集思广益。