【文件属性】:
文件名称:软件课程设计 试验报告 代码 演示
文件大小:1016KB
文件格式:DOC
更新时间:2012-11-27 16:59:42
软件课程设计 报告 实验代码 演示图片
1基础题_2.由计算机生成简单的四则运算题
1.1 需求分析:
本题主要是要求设计一个可以自动生成四则运算的测试器,并且完全由用户决定出加、减、乘、除哪一种运算题,以及出一位数还是两位数的运算题,同时还要对用户给出的答案的对错进行判断。在程序运行过程中,用户可以选择何时结束程序,并在结束程序时给出一个某种形式的成绩。
///////////////////////////////////////////// 程序执行的结果:///////////////////////////////////////////////////
1.2 概要设计:
在对题目理解的基础上,并针对几个特别的技术环节,我认为程序可分为三个部分:
1) 程序的欢迎界面,主要通过一些特殊制表符来完成。其中运行,退出程序可以通过一个while循环来判定同时还要考虑用户输入信号量的正误;
2) 出题函数,也是本程序最关键的一个函数,通过使用“rand()%10”或“rand()%100”来获得一个0到9的一位整数随机值或得到0到99的两位整数随机值来为用户出题,并判断用户答案的对错;
3) 评分系统,是在用户选择退出后对用户所答题情况给出的成绩评价。
///////////////////////////////////////////////////
程序流程图:
1.3 详细设计与编码:
为了使程序更加简洁与工整,且容易修改和阅读,我采用头文件的方式将Exam()函数放在了Exam .h中。Exam()函数主要负责程序的出题和结果的判断,其输入接口为运算符号,位数,即只需向其输入四则运算的一种符号和运算的位数,函数便自动生成题目并自动判断结果的正误,结果以1,0返回。而主程序则是完成了程序的开始、结束,用户成绩的判定。
///////////////////////////////////////////////////
具体源程序如下:
----------------------------------------------------------------------------------------------------------------------
int Exam(int figure, int sign)
{//本函数负责给用户出题
if (figure!=1&&figure!=2&&sign<1&&sign>4) return 0;
//判断函数的输入是否符合要求
int a, b;
if (figure==1)
a=rand()%10; b=rand()%10;
if (figure==2)
a=rand()%100; b=rand()%100;
switch(sign)
{
case(1):
{
cout<<" "<>r;
if(r!=a+b)
{
cout<<" "<<"╳ 很遗憾,回答错误! X﹏X "<>r;
if(r!=a-b)
{
cout<<" "<<"╳ 很遗憾,回答错误! X﹏X "<>r;
if(r!=a*b)
{
cout<<" "<<"╳ 很遗憾,回答错误! X﹏X "<>r;
if(r!=a/b)
{
cout<<" "<<"╳很遗憾,回答错误! X﹏X "<>m;
int N[7]={0,0,0,0,0,0,0}; //用来存储每种面值纸币所需的数目
int Money[7]={100,50,20,10,5,2,1}; //存放7种纸币的面值
for (int i=0; i<7; i++)
{
while (m>=Money[i])
{
m-=Money[i];
N[i]++;
}
}
cout<<"最少使用"<1由用户通过cin输入指定),则该号人员被“淘汰出局”;接着仍沿顺时针方向从被淘汰出局者的下一人员又重新从1开始数起,数到k后,淘汰第2个人;如此继续,直到最后剩下一个人时停止。请输出最后所剩那一个人的编号,并输出淘汰过程的某种“中间结果数据”。
///////////////////////////////////////////// 程序执行的结果:///////////////////////////////////////////////////
3.2 概要设计:
在对题目理解的基础上,以及题目中所给出的要求,我认为此问题可以通过模拟指针循环查找的方法来实现题目所给的限定。在淘汰人员时,我准备利用一个布尔数组来存放这n个人的状态(是否被淘汰),然后通过一个point"指针"对其进行循环查找。而另定义一个j变量来进行报数操作。不但可以实现在时下最后一个人时输出这个人的编号,还可以在每次淘汰人员时,输出被淘汰人员的编号。
///////////////////////////////////////////////////
程序流程图:
3.3 详细设计与编码:
因为总人数是由用户所给定的,所以主函数内的所有涉及n的数组都需要使用动态数组来进行定义。整个报数环节在主函数中体现在一个while循环上,而跳出这个循环的条件便是对队列中人数的判断,即当队列中的人数只剩下一个时,跳出此循环。
///////////////////////////////////////////////////
具体源程序如下:
----------------------------------------------------------------------------------------------------------------------
void main()
{
int n, k;
cout<<"请输入总人数 n:";
cin>>n;
cout<<"请输入报数的最大值 k:";
cin>>k;
bool *p=new bool[n+1]; //布尔 p 数组用来存放 n 个人的状态
for (int i=1; i<=n; i++) p[i]=1;//1 状态在队列里 0 被淘汰了
int point=0, j=0, m=n; //point 编号指针 j 报数 m 队列里剩有的人数
while (true)
{
j++; point++;
if (point==n+1) point=1; //point 指向 n+1 是转到1
while (p[point]==0)
{
point++;
if (point==n+1) point=1;
}
if (j==k) //报数报到 k
{
p[point]=0;
cout<<"编号为 "<>c;
while (c<1||c>3)
{
cout<<"Sorry, your importation contain mistake, please reinput: ";
cin>>c;
}
switch(c)
{//将用户选出的一行分成3份,分布到每一行
case 1:
{
for (i=3; i<6; i++)
swap(line1[i], line2[i]);
for (i=6; i<9; i++)
swap(line1[i], line3[i]);
break;
}
case 2:
{
for (i=0; i<3; i++)
swap(line2[i], line1[i]);
for (i=6; i<9; i++)
swap(line2[i], line3[i]);
break;
}
case 3:
{
for (i=0; i<3; i++)
swap(line3[i], line1[i]);
for (i=3; i<6; i++)
swap(line3[i], line2[i]);
break;
}
}
cout<<"-------------------------------------"<>c;
while (c<1||c>3)
{
cout<<"Sorry, your importation contain mistake, please reinput: ";
cin>>c;
}
switch(c)
{//将用户选出的一行中的3个可能值,分布到每一行的首位
case 1:
{
swap(line1[1], line2[0]);
swap(line1[2], line3[0]);
break;
}
case 2:
{
swap(line2[3], line1[0]);
swap(line2[4], line2[0]);
swap(line2[5], line3[0]);
break;
}
case 3:
{
swap(line3[6], line1[0]);
swap(line3[7], line2[0]);
swap(line3[8], line3[0]);
break;
}
}
cout<<"-------------------------------------"<>c;
while (c<1||c>3)
{
cout<<"Sorry, your importation contain mistake, please reinput: ";
cin>>c;
}
//用户所输入的行数的第一张牌即用户一开始就“暗记”的牌
if (c==1)
cout<<"Your remenber card is: "<0)的数值放到引用Lxn之中(将作为结果返回到主调函数的对应实参变量中),并将倒数第n位(从右边数第n位,n>0)的数值作为函数结果返回去。并编制主函数对它进行调用以验证其正确性。
///////////////////////////////////////////// 程序执行的结果:///////////////////////////////////////////////////
5.2 概要设计:
在对题目理解的基础上,以及题目中所给出的要求,我认为此问题有以下两个重点:
1)将用户输入的这个长整型的数按位存储在一个数组里;
2)通过循环输出这个数组的第n-1项和倒数第n-1项。
///////////////////////////////////////////////////
程序流程图:
5.3 详细设计与编码:
当x=123456789,n=7时,执行语句“Rxn=f(x, n, Lxn);”将使返回的Lxn为7,并使Rxn变为3;而执行语句“Rxn=f(12345, 6, Lxn);”将使Lxn与Rxn都变为为0(超出数的“长度”即总位数时返回0)。
///////////////////////////////////////////////////
具体源程序如下:
----------------------------------------------------------------------------------------------------------------------
int f(unsigned long x, int n, int&Lxn)
{//题目所要求的函数f
int N=1; //用来记录无符长整数x的位数
unsigned long IM=x/10;
while (IM!=0)
{
IM=IM/10;
N++;
}
if (n>N)
{//用来判断n是否超出x的长度
Lxn=0;
return 0;
}
int *p=new int[N+1]; //用来存放x的每一位数
for (int i=N; i>0; i--)
{//将x的每一位数字倒序的输入到数组p中
int j=pow(10,(N-i+1));
p[i]=(x%j-x%(j/10))/(j/10);
}
Lxn=p[n]; //返回引用Lxn的值
return p[N-n+1]; //函数返回的值
}
----------------------------------------------------------------------------------------------------------------------
main()函数见test_Main .cpp
----------------------------------------------------------------------------------------------------------------------
5.4 调试分析:
本程序在调试的过程中,可能会遇到由于长整型数位数的限制,用户如果输入的x太大的话便会产生程序的溢出错误,造成程序进入死循环。所以在输入时,x的大小因有所限制。
5.5 用户使用说明:
在程序运行后需要用户根据程序的提示输入一个长整型的x,在输入要显示的位数n即可让程序将x的第n位和从后数第n位显示出来。
5.6 设计心得:
这道题重点便是怎样将用户输入的长整型数分位存储,当然,我们也可以选用getchar()的方式,但我个人认为还是使用数组来通过取余的方式将x的每一位村与数组中比较好。
在完成程序后,调试是发现了很多的错误,其中取余的地方就一直通不过,在反复调试后才最终将程序改好。通过这次编程使我懂得即使是非常有把握的程序,如果不细心的话,一样会碰钉子。
6基础题_14.整数组前n项是否按降序排列
6.1 需求分析:
本题主要是要求编出两种算法,一种递归一种非递归两种函数f,负责判断数组a的前n个元素是否从大到小完全有序了,是则返回true,否则返回false。
///////////////////////////////////////////// 程序执行的结果:///////////////////////////////////////////////////
6.2 概要设计:
1)非递归函数中只需逐对地判断各a[i] 与a[i+1]是否都已从大到小有序排列(i = 0,1,…,n-2)。
2)递归函数中将问题分解处理为:若n=1(即只有1个元素时)则返回true而递归出口;n>1时,若最后一对元素不顺序则返回false,否则进行递归调用(传去实参a与 n-1,去判断前n-1个元素的顺序性),并返回递归调用的结果(与前n-1个元素的是否顺序性相同)。
///////////////////////////////////////////////////
程序流程图: