标签:分数 结对 项目 Number 生成 运算符 outputStack var
一、详情
课程 | 软件工程 |
---|---|
队伍成员 | 3218005438蔡晓芬、3218005398罗秋彤 |
要求 | 作业需求 |
GitHub | GitHub |
目标 | 四则运算随机生成器 |
二、PSP
PSP2.1 | Personal Software Process Stages | 预估耗时(分钟) | 实际耗时(分钟) |
---|---|---|---|
Planning | 计划 | 80 | 60 |
Estimate | 估计这个任务需要多少时间 | 30 | 20 |
Development | 开发 | 800 | 1000 |
Analysis | 需求分析 (包括学习新技术) | 350 | 200 |
Design Spec | 生成设计文档 | 40 | 30 |
Design Review | 设计复审 | 20 | 30 |
Coding Standard | 代码规范 (为目前的开发制定合适的规范) | 20 | 25 |
Design | 具体设计 | 60 | 40 |
Coding | 具体编码 | 100 | 120 |
Code Review | 代码复审 | 60 | 60 |
Test | 测试(自我测试,修改代码,提交修改) | 120 | 200 |
Reporting | 报告 | 100 | 80 |
Test Repor | 测试报告 | 30 | 30 |
Size Measurement | 计算工作量 | 20 | 10 |
Postmortem & Process Improvement Plan | 事后总结, 并提出过程改进计划 | 50 | 30 |
合计 | 1880 | 1935 |
三、实现流程
四、关键问题
- 随机生成数的生成、多个运算符的生成
- 生成表达式的运算(调度场算法、后缀表达式)
- 分数的计算与化简,随机生成分数
- 题目与答案的导出文件
- 判断导入文件的答题情况
五、代码部分
1.随机生成数的生成、多个运算符的生成
// 随机数生成,通过传入参数Max与Min,生成该范围内的一个随机数
function GetRandomNum(Min,Max){
var Range = Max - Min;
var Rand = Math.random(); //随机生成0.0~1.0的一个数
var x = Min + Math.round(Range * Rand); //确保最小值,取四舍五入的整数
return x;
}
//定义一个运算符的数组,通过随机生成的数组下标,生成一个随机的运算符。
var signArr = ['+','-','*','÷'];
// 随机生成运算符数组下标,最多三个运算符
var s0 = GetRandomNum(0,3);
var s1 = GetRandomNum(0,3);
var s2 = GetRandomNum(0,3);
// 随机生成运算符的个数
var count = GetRandomNum(1,3);
2.生成表达式的运算(调度场算法、后缀表达式)
Ⅰ. 调度场算法: 将中缀表达式转换为后缀表达式的一个算法。
如: 3 + 4 ——> 3 4 +
function schfa(exp){
var inputStack = [];
var outputStack = [];
var outputQueue = [];
for(var i=0,len = exp.length; i<len; i++){
var op = exp[i];
inputStack = exp.split(' '); //将表达式的空格去掉,分裂成数组
}
while(inputStack.length > 0){
var op = inputStack.shift();
// 如果为运算符,当该运算符的优先级小于或等于则压入栈
if(isOperator(op)){
while(prioraty(op,outputStack[outputStack.length - 1]) && (outputStack.length > 0){
outputQueue.push(outputStack.pop());
}
outputStack.push(op);
}else{
outputQueue.push(op);
}
}
while(outputStack.length > 0){
outputQueue.push(outputStack.pop());
}
return outputQueue;
}
Ⅱ. 后缀表达式
function rpn(rpnQueue){
var outputStack = [];
while(rpnQueue.length > 0){
var op = rpnQueue.shift();
if(!isOperator(op)){
outputStack.push(op);
}else{
if(outputStack.length < 2){
throw "unvalid stack length";
}
var num2 = outputStack.pop();
var num1 = outputStack.pop();
outputStack.push(getResult(num1,num2,op));
}
}
if(outputStack.length != 1){
throw "unvalid expression";
}else{
return outputStack[0];
}
}
3. 分数的计算与化简,随机生成分数
Ⅰ. 分数的计算步骤:判断生成数是否为分数,是则通过split()将分数分割为字符串数组,再通过分数的计算方式算出结果
// 以运算符前的数字为分数,后一个数为整数为例
if(num1.toString().indexOf('/') != -1 && num2.toString().indexOf('/' == -1)){
var fraction = num1.split('/');
num2 = Number(num2);
switch(op){
case '+': return (Number(fraction[0]) + Number(fraction[1])*num2 + '/' + Number(fraction[1]));
case '-': return (Number(fraction[0]) - Number(fraction[1])*num2 + '/' + Number(fraction[1]));
case '*': return (Number(fraction[0])*num2 + '/' + Number(fraction[1]));
case '÷': return (Number(fraction[0]) + '/' + (Number(fraction[1])*num2));
default: return 0;
}
}
Ⅱ. 分数的化简
function Fractions (a,b,mf) {
if(a == 0 || b == 0) return 0;
// 当最大公约数为1时,分数不需要化简
if(mf==1) {
if(a>b && b!=1) {
return parseInt(a/b) + "`" + a%b + '/' + b;
} else if(a<b) {
return a + '/' + b;
} else {
return 1;
}
} else {
// 最大公约数不为1,对x,y根据最大公因子进行化简
var x = a/mf;
var y = b/mf;
if(y==1) {
return x;
} else {
return fenShu(x,y, getMaxFactor(x, y));
}
}
}
Ⅲ.随机生成分数
// 随机是否生成分数,布尔值1即为分数
// 以一个运算符为例
var isF = Math.round(Math.random()); //随机生成1或0
switch(count){
case 1:{
for(i=0; i<2; i++){
if(isF){
a[i] = GetRandomNum(1,MAX_NUM) + '/' + GetRandomNum(1,MAX_NUM);;
}else{
a[i] = GetRandomNum(1,MAX_NUM);
}
}
return a[0] + signArr[s0] + a[1];
}
}
4. 题目与答案的导出文件
function download(filename, text) {
var pom = document.createElement('a');
pom.setAttribute('href', 'data:text/plain;charset=utf-8,' + encodeURIComponent(text));
pom.setAttribute('download', filename);
if (document.createEvent) {
var event = document.createEvent('MouseEvents');
event.initEvent('click', true, true);
pom.dispatchEvent(event);
} else {
pom.click();
}
}
六、运行结果
1.初始页面
2.测试用例
3.答案、问题文本导出
七、小结
1.分工明确会更有效率,两个人讨论可以有更多的想法。
2. 不能单纯地通过表达式中的数字直接计算表达式结果,要学会利用栈。
3. ÷ 与 / :因为‘/’也可表示除法,一开始分数与除法运算符都用‘/’表示,虽然方便除法运算,后来发现对于判断分数以及分数的计算十分麻烦,故采用‘÷’。
参考文章
标签:分数,结对,项目,Number,生成,运算符,outputStack,var 来源: https://www.cnblogs.com/avido/p/13806525.html
本站声明: 1. iCode9 技术分享网(下文简称本站)提供的所有内容,仅供技术学习、探讨和分享; 2. 关于本站的所有留言、评论、转载及引用,纯属内容发起人的个人观点,与本站观点和立场无关; 3. 关于本站的所有言论和文字,纯属内容发起人的个人观点,与本站观点和立场无关; 4. 本站文章均是网友提供,不完全保证技术分享内容的完整性、准确性、时效性、风险性和版权归属;如您发现该文章侵犯了您的权益,可联系我们第一时间进行删除; 5. 本站为非盈利性的个人网站,所有内容不会用来进行牟利,也不会利用任何形式的广告来间接获益,纯粹是为了广大技术爱好者提供技术内容和技术思想的分享性交流网站。