您的位置:首页 > 理论基础 > 数据结构算法

中缀表达式转后缀表达式的实现

2017-01-19 17:32 211 查看
中缀表达式转换为后缀表达式的具体实现:
template<class T>
class SqStackClass     //顺序栈类模板;
{
T* data;            //存放栈中元素;
int top;            //栈顶指针;
public:
SqStackClass();    //构造函数;
~SqStackClass();   //析构函数;
bool StackEmpty(); //判断栈是否为空;
bool Push(T e);    //进栈算法;
bool Pop(T &e);     //出栈算法;
bool GetTop(T &e);  //取栈顶元素;
};
template<class T>
SqStackClass<T>::SqStackClass()
{
data=new T [MaxSize];
top=-1;
}
template<class T>
SqStackClass<T>::~SqStackClass()
{
delete [] data;
}
template<class T>
SqStackClass<T>::StackEmpty()
{
return (top==-1);
}

template<class T>
bool SqStackClass<T>::Push(T e)
{
if (top==MaxSize)//表示栈已满;
return false;
top++;
data[top]=e;
return true;
}

template<class T>
bool SqStackClass<T>::Pop(T &e)
{
if (top==-1)
return false;
e=data[top];
top--;
return true;
}

template<class T>
bool SqStackClass<T>::GetTop(T &e)
{
if (top==-1)
return false;
e=data[top];
return true;
}

class ExpressClass   //表达式类;
{
char *exp;
char postexp[MaxSize];
int pnum;
public:
void Setexp(char *str); //获取一个中缀表达式;
void Disppostexp();     //输出后缀表达式;
void Trans();          //中缀表达式转换为后缀表达式;
bool GetValue(double &v);   //计算后缀表达式的值;
};
void ExpressClass::Trans() //将中缀表达式exp转换成后缀表达式postexp
{
SqStackClass<char> op; //运算符栈;
int i=0,j=0;        //中缀表达式exp和后缀表达式postexp的下标;
char ch,e;
while (exp[i])    //中缀表达式未扫描完;
{
ch=exp[i];
if (ch=='(')//如果读取的字符为左括号,直接进栈;
op.Push(ch);
else if (ch==')')
{
while (!op.StackEmpty()&&op.GetTop(e)&&e!=')')
{            //将op栈中左括号‘(’之前的运算符退栈并存放到postexp(后缀表达式中);
op.Pop(e);
postexp[j]=e;
j++;
}
op.Pop(e);//将左括号从栈中弹出;
}
else if (ch=='+'||ch=='-')
{
while(!op.StackEmpty()&&op.GetTop(e)&&e!='(')
{                     //将op栈中左括号‘(’之前的所有运算符弹出符号栈,并存放到后缀
//表达式postexp中;
op.Pop(e);
postexp[j]=e;
j++;
}
op.Push(ch);   //在将‘+'或‘-’进栈
}
else if(ch=='*'||ch=='/')
{
while(!op.StackEmpty()&&op.GetTop(e)&&e!='('&&(e=='*'||e=='/'))
{                           //将op运算符栈中左括号‘(’之前的‘*’或‘/’出栈
//并存放到postexp(后缀表达式中)
op.Pop(e);
postexp[j]=e;
j++;
}
op.Push(ch);//将‘*’或‘/’存入符号栈中;
}
else //处理数字;
{
while(ch>='0'&&ch<='9')
{
postexp[j]=ch;
j++;
i++;
if (exp[i])
ch=exp[i];
else
break;
}
i--;      //中缀表达式中退一个字符;
postexp[j]='#';//用‘#’标识一个数值串的结束;
j++;
}
i++;   //继续处理其他字符;
}
while(!op.StackEmpty())//中缀表达式扫描完毕,符号栈不为空时;
{                       //将栈中的所有符号退栈,并直接添加到后缀表达中;
op.Pop(e);
postexp[j++]=e;
}
pnum=j;
}

bool ExpressClass::GetValue(double &v)
{
SqStackClass<double> st; //运算数栈;
double a,b,c,d;
int i=0;
char ch;
while(i<pnum) //后缀表达式postexp未扫描完时,循环;
{
ch=postexp[i];
switch(ch)
{
case '+':               //判定为‘+’号;
st.Pop(a);          //退栈取数值a;
st.Pop(b);          //退栈取数值b;
c=b+a;
st.Push(c);         //将计算结果进栈;
break;
case '-':
st.Pop(a);
st.Pop(b);
c=b-a;
st.Push(c);
break;
case '*':
st.Pop(a);
st.Pop(b);
c=b*a;
st.Push(c);
break;
case '/':
st.Pop(a);
st.Pop(b);
if (a!=0)
{
c=b/a;
st.Push(c);
}
else
return false;   //如果除0,则错误返回false;
break;
default:        //数字字符进栈;
d=0;
while(ch>='0'&&ch<='9')
{
d=10*d+ch-'0';
i++;
ch=postexp[i];
}
st.Push(d);
break;
}
i++;   //这个地方可以跳过'#';
}
st.GetTop(v);//栈顶的值,即为后缀表达式的值;
return true;
}
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息