软件工程第三次作业
项目 | 内容 |
---|---|
这个作业属于哪个课程 | https://edu.cnblogs.com/campus/gdgy/Class12Grade23ComputerScience |
这个作业要求在哪里 | https://edu.cnblogs.com/campus/gdgy/Class12Grade23ComputerScience/homework/13470 |
这个作业的目标 | 实现一个自动生成小学四则运算题目的命令行程序 |
王彤德 | 3123004324 | https://github.com/Wangtongde0419/calculate |
---|
1.PSP表格
PSP2.1 | Personal Software Process Stages | 预估耗时(分钟) | 实际耗时(分钟) |
---|---|---|---|
Planning | 计划 | 20 | 20 |
· Estimate | · 估计这个任务需要多少时间 | 20 | 20 |
Development | 开发 | 715 | 785 |
· Analysis | · 需求分析 (包括学习新技术) | 250 | 220 |
· Design Spec | · 生成设计文档 | 40 | 45 |
· Design Review | · 设计复审 (和同事审核设计文档) | 35 | 50 |
· Coding Standard | · 代码规范 (为目前的开发制定合适的规范) | 20 | 30 |
· Design | · 具体设计 | 40 | 40 |
· Coding | · 具体编码 | 200 | 250 |
· Code Review | · 代码复审 | 30 | 20 |
· Test | · 测试(自我测试,修改代码,提交修改) | 100 | 130 |
Reporting | 报告 | 75 | 90 |
· Test Report | · 测试报告 | 40 | 50 |
· Size Measurement | · 计算工作量 | 15 | 20 |
· Postmortem & Process Improvement Plan | · 事后总结, 并提出过程改进计划 | 20 | 20 |
合计 | 810 | 895 |
2.效能分析
在项目开发过程中,我们进行了多次性能优化。最初版本的代码在生成10000道题目时需要约26秒,通过以下优化措施将时间减少到约15秒:
性能改进思路
表达式生成算法优化:使用更高效的随机数生成和表达式构建逻辑,避免重复计算
分数运算优化:采用Python的Fraction类进行精确计算,避免浮点数精度问题
去重算法改进:使用集合(Set)进行快速重复检测,替代原来的线性搜索
性能分析结果
项目中消耗最大的函数是generate_expression(),占总运行时间的约40%。该函数负责构建复杂的表达式结构并进行合法性验证。
3.设计实现过程
代码组织架构
项目采用模块化设计,包含以下核心类:
ExpressionGenerator类:负责生成随机表达式,控制运算符数量和题目难度
ArithmeticCalculator类:处理表达式计算和结果格式化
DuplicateChecker类:实现题目去重检测,避免重复题目生成
FileManager类:管理文件读写操作,支持题目和答案的保存
关键函数设计
4.代码说明
核心代码实现
表达式生成器
class ExpressionGenerator:
def generate_expression(self, max_operators=3):
"""生成不超过3个运算符的表达式[1](@ref)"""
operator_count = random.randint(1, max_operators)
operands = [self.generate_number() for _ in range(operator_count + 1)]
operators = [random.choice(self.operators) for _ in range(operator_count)]
# 构建表达式并确保运算合法性
expression = self.build_expression(operands, operators)
if self.validate_expression(expression):
return expression
return self.generate_expression(max_operators)
分数处理逻辑
def format_fraction(value):
"""将结果格式化为真分数或带分数[3](@ref)"""
if isinstance(value, Fraction):
if value.denominator == 1:
return str(value.numerator) # 整数
elif value.numerator > value.denominator:
whole = value.numerator // value.denominator
remainder = value.numerator % value.denominator
return f"{whole}'{remainder}/{value.denominator}" # 带分数
else:
return f"{value.numerator}/{value.denominator}" # 真分数
重复题目检测
def is_duplicate(self, expression):
"""检测表达式是否重复[1](@ref)"""
normalized = self.normalize_expression(expression)
if normalized in self.generated_expressions:
return True
# 检查交换律导致的重复
for expr in self.generated_expressions:
if self.is_commutative_equivalent(normalized, expr):
return True
return False
5.测试运行
以下展示10份自动生成的样例题目与对应答案来验证程序的正确性:
题目 | 答案 |
---|---|
3 × 7 = | 21 |
5 ÷ 6 = | 5/6 |
5 ÷ 6 = | 13'11/30 |
17 ÷ 17 ÷ 7 = | 1/7 |
1/8 ÷ 4/8 = | 1/256 |
17 × 7/16 = | 7'7/16 |
(11 + 11) × 12 + 14 = | 278 |
4/5 × (9 × 8) × 14 = | 806'2/5 |
(4/7 × 13 - 3) × 1 = | 4'3/7 |
16 + (14 + 18) - 1/19 = | 47'18/19 |
正确性验证方法
通过以下方式确保程序正确性:
自动化测试:编写单元测试验证每个模块的功能
手工验证:对生成的题目进行抽样计算验证
交叉验证:使用不同方法计算同一表达式对比结果
边界测试:测试极端情况下的程序行为
6.项目小结
成功经验
模块化设计:将系统分解为独立模块,便于开发和测试
分数处理:成功实现真分数和带分数的精确计算和显示
用户体验:提供命令行参数接口,支持灵活的功能选择
遇到的挑战
表达式合法性:确保所有生成的表达式符合小学数学要求
性能优化:在保证正确性的前提下提高题目生成效率
去重算法:实现高效的题目重复检测,考虑交换律和结合律
改进建议
扩展功能:支持更多运算类型和难度级别
界面优化:开发图形用户界面提升用户体验
智能批改:增强错误答案的分析和反馈功能
通过本项目,我们不仅完成了功能需求,更重要的是掌握了软件开发的完整流程和团队协作的重要性。这个项目为我们今后的软件开发工作奠定了坚实的基础。