利用栈将中缀算数表达式变换成后缀算术表达式并计算(0-9)

it2023-10-31  80

#include <iostream> #include <stack> #include <math.h> #define maxsize 20 using namespace std; class Calculator { public: Calculator(){while(s.empty()==false)s.pop();} void Run(char *ch); void Clear(); private: stack<int> s; void AddOperator(int value); bool Get2Operands(int& left,int& right); void DoOperator(char op); }; void Calculator::DoOperator(char op) //私有函数:取两个操作数,根据操作符op形成运算指令并计算 { int left,right,value; bool result; result=Get2Operands(left,right);//取两个操作数 if(result==true)//如果操作数取成功,计算并进栈 switch(op){ case'+':value=left+right;s.push(value);break;//加 case'-':value=left-right;s.push(value);break;//减 case'*':value=left*right;s.push(value);break;//乘 case'/':if(right==0.0){//若除0,报错,清栈 cerr<<"Divide by 0!"<<endl; Clear(); } else{ value=left/right;s.push(value); } break;//没有除0,做除法 } else Clear();//取操作数出错,清栈 } bool Calculator::Get2Operands(int &left,int& right) //私有函数:从操作数栈中取出两个操作数 { if(s.empty()==true){//检查栈空否 cerr<<"缺少右操作数!"<<endl;//栈空,报错 return false; } right=s.top();//取右操作数 //cout<<"右操作数:"<<right<<endl; s.pop();//右操作数退栈 if(s.empty()==true){//检查栈空否 cerr<<"缺少左操作数!"<<endl;//栈空,报错 return false; } left=s.top();//取左操作数 //cout<<"左操作数:"<<left<<endl; s.pop();//左操作数退栈 return true; } void Calculator::AddOperator(int value) //私有函数:将操作数的值value进操作数栈 { s.push(value); } void Calculator::Run(char *ch) //读字符串并求一个后缀表达式的值。以字符‘#’结束 { //char ch; int newOperand; char *p=ch; while(*p!='#'){ //cout<<*p<<endl; switch(*p){ case'+': case'-': case'*': case'/':DoOperator(*p);break;//是操作数,执行计算 default://cin.putback(*p);//将字符放回输入流 //cin>>newOperand;//重新读操作数 newOperand=*p-48; AddOperator(newOperand);//将操作数放入栈中 } p++; } cout<<"="<<s.top()<<endl; } void Calculator::Clear() //清栈 { while(s.size()>0) s.pop(); } int isp(char ch) //栈内优先数 { int num=-1; switch(ch){ case'#':num=0;break; case'(':num=1;break; case'*': case'/': case'%':num=5;break; case'+': case'-':num=3;break; case')':num=6;break; } return num; } int icp(char ch) //栈外优先数 { int num=-1; switch(ch){ case'#':num=0;break; case'(':num=6;break; case'*': case'/': case'%':num=4;break; case'+': case'-':num=2;break; case')':num=1;break; } return num; } void postfix() //将中缀表达式转换为后缀表达式,表达式收尾字符均为‘#’ { stack<char> s;//定义栈的对象s,其元素为字符 char ch='#',ch1,op,p[maxsize]; int i=0; s.push(ch);//栈底存放‘#’ cin.get(ch);//读入下一个字符 while(s.empty()==false && ch!='#') if(isdigit(ch)){//判断加粗样式是否为操作数 cout<<ch; p[i]=ch;i++; cin.get(ch); } else{ ch1=s.top();//取栈顶操作符ch1 if(isp(ch1)<icp(ch)){//新输入操作符ch优先级高 加粗样式 s.push(ch);//进栈 cin.get(ch);//读下一字符 } else if(isp(ch1)>icp(ch)){//新输入操作符ch优先级低 op=s.top();//退栈 s.pop(); cout<<op; p[i]=op;i++; } else{ op=s.top();//输入操作符优先级等于栈顶优先级 s.pop(); if(op=='(') cin.get(ch); } } Calculator CAL; CAL.Run(p); } int main() { postfix(); system("pause"); return 0; }
最新回复(0)