数据结构(栈的补充三)

100 阅读2分钟
  • 用栈求后缀表达式值(把中缀表达式转成后缀表达式,再用栈求值)

从左到右扫描,当遇到操作数的时候就入栈,当遇到运算符的时候就从栈顶弹出两个操作数,结合这个运算符计算结果(注意:第一个弹出的操作数在右边,第二个弹出的操作数在左边),将计算的结果压入栈中,如此进行下去,那么表达式被扫描完之后,整个计算过程也就结束了。

float calPostFix(char exp[]) //float返回值类型
{
    float s[maxSize]; int top = -1; 
    int i=0;
    while (exp[i] != '\0') //for(int i=0;exp[i]!='\0';++i)
    {
        if ('0'<=exp[i] && exp[i]<='9') //判断字符是否是数字
            s[++top]=exp[i]-'0';        //将字符型数字转化成数值型数字的方法
        else if (exp[i] == '+' ||
                 exp[i]=='-' ||
                 exp[i]=='*' ||
                 exp[i] == '/')  //可直接省略成else
        {
            float opnd1,opnd2,result; 
            char op; 
            int flag;
            opnd2=s[top--];  //第二个操作数先出栈
            opnd1 = s[top--];//第一个操作数后出栈
            op=exp[i];
            flag = calSub(opnd1,op,opnd2,result); 
            if (flag == 0){ //计算失败
            {
                std::cout<<"ERROR"<<std::endl; //puts("ERROR"); 
                break;
            }
            s[++top]=result;
        }
        ++i;
    }
    return s[top];//没有栈中元素剩余的情况,直接返回结果
}

  • 用栈求前缀表达式值

这个过程就和求后缀表达式值非常类似,只不过是在很多方面上体现了一个相反的过程。具体就是需要从右往左扫描,遇到操作数就让它入栈,遇到运算符就出战两个操作数,不同的是这次我们构造子表达式的时候,是先出栈的操作数在左边,后出栈的操作数在右边(先出栈的数与扫描方向一致),其他的就和后缀式求值没什么区别了。

求前缀式值后缀式值比求中缀式值简单,前者只需要一个栈且不需要考虑括号,后者需要两个栈且需要考虑括号,把后者转化成前者就是因为求值简单且节省空间
float calPreFix(char exp[],int len) //float返回值类型
{
    float s[maxSize]; int top = -1; 
    int i=len-1;
    while (i>=0) //for(int i=len-1;i>=0;--i)从右往左扫描
    {
        if ('0'<=exp[i] && exp[i]<='9') //判断字符是否是数字
            s[++top]=exp[i]-'0';        //将字符型数字转化成数值型数字的方法
        else if (exp[i] == '+' ||
                 exp[i]=='-' ||
                 exp[i]=='*' ||
                 exp[i] == '/')  //可直接省略成else
        {
            float opnd1,opnd2,result; 
            char op; 
            int flag;
            opnd1=s[top--];  //第二个操作数先出栈
            opnd2=s[top--];//第一个操作数后出栈
            op=exp[i];
            flag = calSub(opnd1,op,opnd2,result); 
            if (flag == 0){ //计算失败
            {
                std::cout<<"ERROR"<<std::endl; //puts("ERROR"); 
                return 0;
            }
            s[++top]=result;
        }
        --i;
    }
    return s[top];//没有栈中元素剩余的情况,直接返回结果
}