计算器 c语言课程设计.docx
- 文档编号:26480314
- 上传时间:2023-06-19
- 格式:DOCX
- 页数:10
- 大小:18.57KB
计算器 c语言课程设计.docx
《计算器 c语言课程设计.docx》由会员分享,可在线阅读,更多相关《计算器 c语言课程设计.docx(10页珍藏版)》请在冰豆网上搜索。
计算器c语言课程设计
设计分析:
我做的是一个计算器程序,属于B级。
题目要求如下:
1、完善计算器程序,改为可对实数操作。
2、完善程序,改为多个操作数基本四则运算,遇到z为止。
3、增加函数,完成四则混合运算,增加相应的主菜单选项
4、添加语句,使四则运算具有测试功能。
5、可扩充其功能。
所给的计算器源程序中已有基本的加、减、乘、除和开方运算,我所要做的就是添加一个可以进行四则混合运算功能的类。
本程序所要用到的头文件有如下几种:
process,iostream,conio,stdlib,math和assert.
原程序中已经定义了加、减、乘、除和开方的运算,它用了类oopcalc将这几个基本运算进行封装。
类中包含以下几个函数:
voidcalcadd();
voidcalcsub();
voidcalcdiv();
voidcalcmult();
voidcalcfartocel();
voidcalcceltofar();
voidcalcsroot();
voidexitprog();
voidmenu();
voidbadinput();
每个函数的参数形式如下:
intadd(floatx,floaty);
intsub(floatx,floaty);
intdiv(floatx,floaty);
intmult(floatx,floaty);
intfartocel(floatx);
intceltofar(floatx);
intsqroot(floatx);
原程序对这几个函数分别做了如下定义:
intoopcalc:
:
add(floatx,floaty)
{
val=x+y;
returnval;
}
intoopcalc:
:
sub(floatx,floaty)
{
val=x-y;
returnval;
}
intoopcalc:
:
div(floatx,floaty)
{
val=x/y;
returnval;
}
intoopcalc:
:
mult(floatx,floaty)
{
val=x*y;
returnval;
}
intoopcalc:
:
fartocel(floatx)
{
intcel=((x-32)*5)/9;
returncel;
}
intoopcalc:
:
celtofar(floatx)
{
intf;
f=x*9/5+32;
returnf;
}
intoopcalc:
:
sqroot(floatx)
{
intg=sqrt(x);
returng;
}
首先要把程序改为可对实数进行操作,由于原程序中的操作数类型都是整形,因此我所采用的办法就是把“int”依次改成“float”。
这是最简单的修改办法,也是最有效的修改办法。
在menu()函数中使用了switch()语句来对功能进行选择,以便于操作。
不同的数字则对应不同的功能。
下面所要进行的修改就是添加四则运算功能。
首先在switch()语句中添加一个新的选项,以用于作为进行四则运算的入口。
然后设计一个简单的计算器类,增加四则运算功能。
简单的运算只要求有两个操作数,如原程序中的加、减、乘除。
而所增加的四则运算则要求输入多个操作数,有计算机自己通过程序来解决多个数字的运算。
这就要求设计的程序能够自动辨别“+”,“-”,“*”,“/”的优先级和结合性。
在这里,我运用了栈的功能进行对程序的修改。
设有表达式:
a+b*c-d/e=
为实现运算符的优先级,采用两个栈:
一个数栈,一个运算符栈。
数栈暂时存放操作数,运算符栈暂时存放运算符。
从左向右扫描算术表达式,遇到操作数,压入数栈;遇到运算符,则与运算符栈栈顶的运算符比较优先级。
若新的运算符优先级高或运算符栈空,则压栈;否则,将栈顶运算符出栈,与数字栈出栈的两个数据进行运算,结果压入数栈,再将新运算符压栈。
继续扫描,直到遇到=号,扫描结束。
栈中数据继续按前面规则出栈。
上面所列表达式运算过程如下图所示:
(A)(B)(C)(D)(E)
NONONONONO
----------
----------
--—>e--->---->---->--
c-b*c->t1d/d/e->t2t2-t1-t2->t3--a+t3->t4--
b*t1_t1_t3---
a+a+a+a+--
首先a入数栈,“+”入运算符栈,b入数栈,“*”入运算符栈,c入数栈,见图(A);再扫描到“-”号,则“*”和c、b出栈,b*c得t1压入数栈,“-”号压入运算符栈,“/’号压入运算符栈,e压入数栈,遇到=,扫描结束,见图(B);”/“号弹出运算符栈,e、d弹出数栈,d/e得t2压数栈,见图C;”-“号出栈,t2、t1出栈,t1-t2得t3、t4压栈,见图(D);”+“号出栈,t3、a出栈,栈全空,a+t3得t4,即运算结果。
增加四则混合运算的功能要解决的问题是怎样使计算机能分辨出运算符的优先级。
这里我想到了我们上课学的栈和链表的知识这题我用到了链栈。
首先建立一个链栈的类模板和一个结点链表。
template
这一行是类结点的声明。
因为在类中也同样遵循“先声明后使用”的原则。
template
Tinfo;
Node
public:
Node(Tdata=0,Node
{
info=data;
link=next;
}
friendclassStack
};
这一段是结点模板的定义。
Info是结点,“Node
“friendclassStack
“info=data;”设置第一个接点的值,“link=next;”把下一个指针的值赋给link指针。
template
Node
public:
Stack(){top=NULL;}
~Stack();
voidPush(constT&data);
TPop();
TGetTop();
voidMakeEmpty();
boolIsEmpty(){returntop==NULL;}
};
这一段是类模板的定义。
其中“Node
“Stack()”是类的构造函数,在构造函数中把栈顶指针指向NULL.“~Stack()”是析构函数。
“voidPush(constT&data)”是用于压栈的函数。
“TPop()”是用于将数据弹出栈的函数。
“TGetTop()”是用于取栈顶元素的函数。
“voidMakeempty()”是用于将栈中的元素清空的函数。
template
:
MakeEmpty(){
Node
while(top!
=NULL){temp=top;top=top->link;deletetemp;}
}
这一段是对清空链表的函数进行定义。
设置了一个指针temp,当头结点不等于NULL是进行while循环。
循环是将头结点的值赋给temp,再把头结点的指针指向下一个结点。
template
:
Push(constT&data){
top=newNode
}
链栈向前生成,新压栈的结点在链栈头
template
:
Pop(){
assert(!
IsEmpty());
Node
Tdata=temp->info;
top=top->link;
deletetemp;
returndata;
}
这是对弹出函数的定义。
“top=top->link;”丢弃栈顶结点。
“deletetemp;”释放栈顶结点。
“returndata;”返回栈顶数据。
classCalculator{
Stack
Stack
public:
Calculator(void){};
voidCal(void);//计算器运算程序
voidGetTowNum(int&Num1,int&Num2);
voidCompute(charOpr);
voidClear(void);
};
这是简单计算器的类定义。
在这个类里,将链栈Nstack和Ostack都定义为了私有函数,还声明了一个构造函数“Calculator(void){};”。
“voidClear(void);”是用于清空计算器数据的函数,其中分别调用了“Nstack.MakeEmpty();”和“Ostack.MakeEmpty();”。
“voidGetTowNum(int&Num1,int&Num2);”定义了两个数字Num1和Num2,调用了函数“Nstack.Pop();”。
“voidCompute(charOpr);”则定义了各种运算符的计算,这些运算符是“+”、“-”、“*”、“/”和“=”。
“voidCal(void);”是简易的计算器程序,定义如下:
voidCalculator:
:
Cal(){
cout<<"进行四则运算:
"< boolb1=true,b2=true;//用布尔型定义两个变量 charch1,ch2,str[50];//定义了三个字符型变量 intk=-1; while(b2){//while循环 cin>>ch1; if(ch1>='0'&&ch1<='9'){//判断ch1是否满足条件 k++;//k自增 str[k]=ch1;//数字字符添入串中 } else{ if(k>=0){ str[k+1]='\0';//数字串生成 Nstack.Push(atoi(str));//数字串转换为整数后压栈 k=-1; } switch(ch1){//用switch语句对不同的运算符进行定义 case'c': Clear();//清空栈 break; case'+': case'-': while(! Ostack.IsEmpty()){ ch2=Ostack.Pop();//不会有比+、-优先级低的 Compute(ch2); } Ostack.Push(ch1); break; case'*': case'/': while(! Ostack.IsEmpty()&&b1){ ch2=Ostack.Pop();//弹出栈顶运算符 if(ch2=='*'||ch2=='/')//比较优先级 Compute(ch2);//新的优先级并不高 else{//新的优先级高 Ostack.Push(ch2);//先把原栈中的运算符压回去 b1=false; } } Ostack.Push(ch1);//再把新的运算符压栈 b1=true;//此句保证乘除从左到右进行 break; case'=': while(! Ostack.IsEmpty()){ ch2=Ostack.Pop(); Compute(ch2); } Compute(ch1); break; } if(ch1=='z')b2=false;//当输入z时结束程序 } } } 在Menu函数中也用了switch函数来把所选菜单项和对应的函数联系起来。 比如在操作时选了“3”,则对应的调用除法函数calcdiv(),其他的运算符也是一样。 voidmain() { oopcalcs; s.menu(); Calculatorp; } 主函数很简单,只定义了一个类oopcalc的对象s和类Calculator的对象p以及对象s的函数menu(). 我的整个的计算器程序编辑思路就是上面的容,通过这次短学期的C++程序设计的学习,我对C++的理解和操作都有了比较大的进步。 C++是一门很有实用价值的科目,它是所有程序设计语言中最有活力和应用最广泛的一种。 它对我们的逻辑思维有很高的要求,很好的训练了我们的思维能力。 这次的设计作业对我们来说也是一次自我的检验和挑战。 在此之前我们从来没有自己动手做过一个这么大的完整的程序,所以在这次的作业过程中我们遇到了很多的困难。 但是正是这些困难让我们更加了解了C++的程序设计的精华,让我们对C++有了更正确的认识。
- 配套讲稿:
如PPT文件的首页显示word图标,表示该PPT已包含配套word讲稿。双击word图标可打开word文档。
- 特殊限制:
部分文档作品中含有的国旗、国徽等图片,仅作为作品整体效果示例展示,禁止商用。设计者仅对作品中独创性部分享有著作权。
- 关 键 词:
- 计算器 c语言课程设计 语言 课程设计