自动生成小学四则运算题目并进行效能分析-改进版
Posted lzhida
tags:
篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了自动生成小学四则运算题目并进行效能分析-改进版相关的知识,希望对你有一定的参考价值。
github地址:https://github.com/lzhida/First-assignment/tree/newbranch
改进:
可以删除一些无意义的括号
题目要求:
1、能自动生成小学四则运算题目,并且不能出现负数;
2、支持真分数四则运算
PSP表格
预计耗时(分钟) | 是实际耗时(分钟) | ||
Planning | 计划 | 30 | 30 |
·Estimate | 估计这个任务需要多少时间 | 180 | 240 |
Development | 开发 | 150 | 180 |
·Analysis | 需求分析 | 5 | 10 |
·Design Spec | 生成设计文档 | 30 | 30 |
·Design Review | 设计复审(和同事审核设计文档) | 5 | 5 |
·Coding Standerd | 代码规范(为目前的开发制定合适的规范) | 5 | 5 |
·Design | 具体设计 | 5 | 10 |
·Coding | 具体编码 | 90 | 110 |
·Code Review | 代码复审 | 5 | 5 |
·Test | 测试(自测,修改代码,提交修改) | 5 | 5 |
Reporting | 报告 | 30 | 80 |
·Test Report | 测试报告 | 10 | 60 |
·Size Measurement | 计算工作量 | 5 | 10 |
·Postmortem & Process Improvement Plan | 事后总结,并提出过程改进计划 | 5 | 10 |
Sum | 合计 | 240 | 260 |
解题思路:
(1)生成四则运算表达式
(2)计算表达式结果
(3)定制一定数量的四则运算题
解题过程:
(1)get_expression():生成一个表达式
(2) get_num():生成一个数字
(3)get_symbol():生成一个符号
(4)expression_generate():生成表达式
(5)compare(symbol_1, symbol_2):比较符号优先级
(6)one_calculate(num, symbol):进行一次运算
(7)calculate(expression):计算整个表达式
(8)output_expression(expression):规范表达式输出
(9)main():定制生成的题目
代码如下:
1 from fractions import Fraction 2 import random 3 4 def get_expression(): 5 """ 6 获得一个四则运算表达式 7 支持整数和真分数混合运算 8 返回数组 9 :return: list 10 """ 11 n = random.randint(1,2) #表达式长度 12 expression = list() # 结果 13 14 for i in range(n): 15 expression.append(get_num()) 16 if i != n - 1: # 当不是最后一个数时,添加一个运算符 17 expression.append(get_symbol()) 18 19 return expression 20 21 def get_num(): 22 """ 23 随机获得一个整数或真分数 24 返回Fraction对象 25 :return: Fraction 26 """ 27 m = random.random() 28 if m >= 0.1: # 整数 29 a = random.randint(1,20) 30 x = Fraction(a) 31 else: # 真分数 32 a = random.randint(1, 20) 33 b = random.randint(1, 20) 34 x = Fraction(a, b) 35 return x 36 37 def get_symbol(): 38 """ 39 获得随机运算符号 40 输入0-3的整数 41 输出字符串 42 :param r: int 43 :return: string 44 """ 45 r = random.randint(0,3) 46 if r == 0: 47 return ‘+‘ 48 elif r == 1: 49 return ‘-‘ 50 elif r == 2: 51 return ‘*‘ 52 elif r == 3: 53 return ‘/‘ 54 55 56 def expression_generate(): 57 """ 58 生成一个表达式 59 带括号 60 :return: 61 """ 62 n = random.randint(1,3) 63 expr = [] 64 for i in range(n): 65 e = get_expression() 66 if len(e) > 1: # 当表示式长度大于1时可以加括号 67 m = random.random() 68 if m > 0.8: # 判断是否加括号 69 expr = expr + e 70 elif m > 0.4: # 是否加嵌套的括号 71 expr.insert(0, ‘(‘) 72 expr = expr + e 73 expr.append(‘)‘) 74 else: # 是否直接在表达式两端加括号 75 expr.append(‘(‘) 76 expr = expr + e 77 expr.append(‘)‘) 78 else: # 表达式长度小于1 79 expr = expr + e 80 if i != n-1: # 判断是否是最后一个表达式,是则不加运算符 81 expr.append(get_symbol()) 82 83 84 return expr 85 86 def compare(symbol_1, symbol_2): 87 """ 88 比较两个符号的优先级 89 */的优先级高于+-的优先级 90 如果symbol_1的符号优先级高于symbol_2的优先级返回True,否则返回Fals 91 :param symbol_1: 92 :param symbol_2: 93 :return: 94 """ 95 if symbol_1 in ["*", "/"] and symbol_2 in ["+", "-"]: 96 return True 97 else: 98 return False 99 100 def one_calculate(num, symbol): 101 """ 102 计算一次四则运算 103 :param num: list 104 :param symbol: list 105 :return: 106 """ 107 b = num.pop() 108 a = num.pop() 109 s = symbol.pop() 110 if s == ‘+‘: 111 result = a + b 112 elif s == ‘-‘: 113 result = a - b 114 elif s == ‘*‘: 115 result = a * b 116 elif s == ‘/‘: 117 result = a / b 118 119 num.append(result) 120 121 def calculate(expression): 122 """ 123 计算表达式的结果 124 输入表达式 125 输出结果 126 :param expression: string 127 :return: int or float 128 """ 129 num = [] 130 symbol = [] 131 i = 0 132 while i < len(expression): # 取出表达式的值 133 if isinstance(expression[i], Fraction): # 如果是数字则加到num中 134 num.append(expression[i]) 135 elif expression[i] == ")": # 如果是")",则symbol出栈并计算结果,直到遇到"(" 136 while symbol[-1] != "(": 137 one_calculate(num, symbol) 138 symbol.pop() 139 elif not symbol or symbol[-1] == "(": # 如果栈为空,或栈顶为"(",直接进栈 140 symbol.append(expression[i]) 141 elif expression[i] == "(" or compare(expression[i], symbol[-1]): # 如果表达式的值为"(",或比栈顶的优先级高,则进栈 142 symbol.append(expression[i]) 143 else: # 其他情况 144 while symbol and not compare(expression[i], symbol[-1]): # 栈不为空,且优先级比栈顶低,则直接进行运算 145 if symbol[-1] == "(": # 直到栈顶为"(",退出 146 break 147 one_calculate(num, symbol) # 计算 148 symbol.append(expression[i]) # 进栈,优先级高 149 i += 1 150 while symbol: # 将栈清空,全部计算完毕 151 one_calculate(num, symbol) 152 153 return num.pop() 154 155 def output_expression(expression): 156 """ 157 使输出的表达式更规范 158 输入表达式数组 159 输出表达式字符串 160 :param expression: list 161 :return: string 162 """ 163 result = str() 164 n = len(expression) 165 for i in range(n): 166 if expression[i] == ‘/‘: 167 result = result + ‘÷‘ 168 elif expression[i] == ‘*‘: 169 result = result + ‘x‘ 170 else: 171 result = result + str(expression[i]) + ‘‘ 172 return result 173 174 175 def test_brackets(expression): 176 """ 177 删除无意义的括号 178 """ 179 i = 1 180 a = 0 181 if len(expression) <= 3: 182 return expression 183 184 while i < len(expression): 185 if expression[i-1] == "(": 186 a += 1 187 b = 0 188 j = i 189 while j < len(expression): 190 if expression[j] == ")": 191 b += 1 192 if a == b: 193 break 194 j += 1 195 196 temp = expression[:] 197 del temp[j] 198 del temp[i-1] 199 if calculate(temp) == calculate(expression): 200 expression = temp[:] 201 a -= 1 202 i += 1 203 return expression 204 205 206 def main(): 207 """ 208 主函数 209 :return: 210 """ 211 n = int(input(‘输入题目的个数:‘)) 212 lis = list() 213 while True: # 直到满足题目个数,结束 214 expression = expression_generate() # 获取表达式 215 expression = test_brackets(expression) # 删除无意义的括号 216 result = calculate(expression) # 计算表达式 217 if float(result) >= 0: # 将表达式和结果保存到字典中 218 dic = dict() 219 expression = output_expression(expression) 220 dic[‘expression‘] = expression 221 dic[‘result‘] = str(result) 222 lis.append(dic) # 把字典添加到列表中 223 if len(lis) >= n: # 当列表长度大于等于题目个数时,退出循环 224 break 225 226 print(‘保存数据到文本‘) 227 with open(‘result.txt‘, ‘w‘) as file: 228 for i in range(len(lis)): 229 file.write(lis[i][‘expression‘] + ‘ = ‘ + lis[i][‘result‘] + ‘ ‘) 230 231 232 if __name__ == ‘__main__‘: 233 main()
效能分析:
以上是关于自动生成小学四则运算题目并进行效能分析-改进版的主要内容,如果未能解决你的问题,请参考以下文章