Task2 四则运算2
1.任务要求:对之前的自动出题系统提出了新的要求:(1)、题目避免重复;(2)、可定制(数量/打印方式);(3)可以控制下列参数:是否有乘除法、数值范围、加减有无负数、除法有无余数、是否支持分数...
2.设计思路:(1)主函数中有一个大循环,其中主框架是一个switch语句构成的,可以在四中运算中设置不同的要求并加以 实现。并使程序可以循环运行,即用户可以循环使用;
(2)避免重复:可以使用srand函数确保产生的随机数不相同;
(3)定制数量/打印方式:每一次循环会出n道题目,每行有num道题目,添加变量N,num,其数值由用户确定;
(4)乘除法选择:有无乘除法,加一个变量mul,设置其值并在switch语句中使用,若有乘除法则执行rand()%4,产生 四种运算符号,反之产生加减两种运算;
(5)数值范围:两个运算数为可以随便设置范围,其中用判断语句确保除法中除数不等于0;减法中被减数大于减数;
(6)除法是否有余数/是否支持分数:添加函数,利用判断语句设定,当题目是除法时如果不能除尽则重新生成题目,直到余 数为零,在主函数合适位置处调用添加函数,使用户可以进行选择题目中是否包含分数的运算数,如果包括可以重新设置 两个运算数变量的格式改为分数,反之不用做处理,并对此函数进行调用。
3.源程序代码:
//四则运算2. 2015/3/13 刘子晗 #include <iostream> #include<stdlib.h> #include <time.h> #include<iomanip> using namespace std; void main() { cout << "欢迎进入四则运算出题系统!" << endl; cout << "*****************************************" << endl; char g='Y',mod; while (g == 'Y') { cout << "此系统分为两个模块,请进行选择:(A.整数 or B.分数)"; cin >> mod; if (mod == 'A') { int N,max,min,num,j; char mul,neg,rem; srand((unsigned)time(NULL)); cout << "请输入要生成的题目数量N:"; cin >> N; cout << "打印参数num(每一行有num道题目):"; cin >> num; cout << "运算数的范围上限max:"; cin >> max; cout << "运算数的范围下限min:"; cin >> min; cout << "您是否希望题目中出现乘除运算?(Y(是)or N(否)):"; cin >> mul; cout << "您是否希望减法题目中出现负数?(Y(是)or N(否)):"; cin >> neg; cout << "您是否希望除法题目中出现余数?(Y(是)or N(否)):"; cin >> rem; for (int k=0;k<N;k++) { int a = rand()%(max-min+1) + min ; int b = rand()%(max-min+1) + min ; if (mul == 'Y') { j = rand()%4 + 1; } if (mul == 'N') { j = rand()%2 + 1; } switch(j) { case 1: cout << setw(3) << a << "+" << setw(3) << b << "=" ; break; case 2: if (neg == 'N') { while (a <= b) { a = rand()%(max-min+1) + min ; b = rand()%(max-min+1) + min ; } cout << setw(3) << a << "-" << setw(3) << b << "=" ;break; } else { cout << setw(3) << a << "-" << setw(3) << b << "=" ;break; } case 3: cout << setw(3) << a << "*" << setw(3) << b << "=" ; break; case 4: while (b == 0) { b = rand()%(max-min+1) + min ; } if (rem == 'N') { while((a % b)!= 0) { a = rand()%(max-min+1) + min ; b = rand()%(max-min+1) + min ; } cout << setw(3) << a << "/" << setw(3) << b << "=" ;break; } else { cout << setw(3) << a << "/" << setw(3) << b << "=" ;break; } } if ( (k+1) % num == 0) { cout << endl; } else { cout << " "; } } } else { int N,max,min,num,j; char mul,neg; srand((unsigned)time(NULL)); cout << "请输入要生成的题目数量N:"; cin >> N; cout << "打印参数num(每一行有num道题目):"; cin >> num; cout << "运算数的分子和分母的范围上限max:"; cin >> max; cout << "运算数的分子和分母的范围下限min:"; cin >> min; cout << "您是否希望题目中出现乘除运算?(Y(是)or N(否)):"; cin >> mul; cout << "您是否希望减法题目中出现负数?(Y(是)or N(否)):"; cin >> neg; for (int k=0;k<N;k++) { int a1 = rand()%(max-min+1) + min ; int a2 = rand()%(max-min+1) + min ; int b1 = rand()%(max-min+1) + min ; int b2 = rand()%(max-min+1) + min ; while(a2==0 || b2==0) { a2 = rand()%(max-min+1) + min ; b2 = rand()%(max-min+1) + min ; } if (mul == 'Y') { j = rand()%4 + 1; } if (mul == 'N') { j = rand()%2 + 1; } switch(j) { case 1: cout << "(" << setw(2) << a1 << "/" << setw(2) << a2 << ")" << "+" << "(" << setw(2) << b1 << "/" << setw(2) << b2 << ")" << "="; break; case 2: cout << "(" << setw(2) << a1 << "/" << setw(2) << a2 << ")" << "-" << "(" << setw(2) << b1 << "/" << setw(2) << b2 << ")" << "="; break; case 3: cout << "(" << setw(2) << a1 << "/" << setw(2) << a2 << ")" << "*" << "(" << setw(2) << b1 << "/" << setw(2) << b2 << ")" << "="; break; case 4: while (b1 == 0) { b1 = rand()%(max-min+1) + min ; } cout << "(" << setw(2) << a1 << "/" << setw(2) << a2 << ")" << "*" << "(" << setw(2) << b1 << "/" << setw(2) << b2 << ")" << "="; break; } if ( (k+1) % num == 0) { cout << endl; } else { cout << " "; } } } cout << "您是否要继续答题?请输入:(Y(是)or N(否))"; cin >> g; cout << "*****************************************" << endl; } cout << "感谢您的使用,再见!"; }
4.运行结果:
5.总结:(1)每一次真正编程序的时候会和自己的预想有很多偏差,主要有以下几点:思路设计的时候想把主函数设计得很简单,然后通过函数调用实现其他功能,但在实现的时候发现把功能实现都涵盖在主函数中也很简单,而且这样思路会变得很清晰;对避免重复题目这一点上,本来想通过三个字符的比较,可是觉得这种方法不够简便,于是采用了srand函数来实现这一功能;再就是在分数的选择上,如果添加函数实现的话,编写测试了好几次都没有成功,于是就在开始的地方设置了一个选择模块使整数和分数的运算区分开来以实现最终的结果。
(2)错误记录:出现的错误有很多,主要有a.由于程序是分块完成的,中间调试的时候出现了错误,if语句中把“==”写成了“= ;
b.在switch语句中,减法和除法的地方由于有判断语句,其中if循环中第一个输出的地方没有加break,虽然没有bug,但是最终运行时总是不对,发现是在条件不满足时就会没有显示该次循环输出结果,加上之后就对了;”;
c.开始实现打印输出设置一行题目数量时用了一个for循环,总是不对,又改成用if判断实现;之后意识到是因为上面的错误造成的而不是这个循环出错了,两种方法皆可;
d.由于数是随机产生的,一位数两位数或三位数都有可能,所以不能保证每一列都是齐的,之后查阅相关资料利用setw()加以纠正即可。
(3)感受:a.之前编写程序的时候我会习惯把相似的一个作为模版去改,从而实现自己所要实现的功能,但是现在突然觉得那是很不明智的,在自己给程序构想出大致框架后一点一点填东西似乎更容易达到预期;
b.编程实现某个功能的时候某种方法行不通时,有必要尽快跳出来,利用查资料或是别的途径看是否有别的简单易行的办法,否则会很耽误时间;在每一次编程中没准都会学到以前没有用过的一些知识点;
c.调试的时候出现的bug要仔细的分析一下,不能太盲目地认为提示行就是错误所在,因为有时候不是;
d.没有错误运行结果却跟自己预期不同或明显有错的时候,要看是哪个错,然后观察相应的程序块加以改正,否则全面找的话会很难找到。
(4)时间表: