zoukankan      html  css  js  c++  java
  • 中缀表达式和逆波兰表达式

    1.中缀表达式

    1)标准四则运算的表达式就叫中缀表达式

    2.逆波兰表达式

    1)逆波兰表达式(后缀表达式):字符串中只有数字和运算符,没有括号,所有运算符号位于操作数之后

    3.中缀表达式转逆波兰表达式

    1)运算符优先级:乘除大于加减,右括号必须匹配左括号

    2)遍历中缀表达式,遇到数字,输出到后缀表达式

    3)遇到运算符:

    • 先判断栈是否为空,若是,则直接将此操作符压入栈
    • 若为'(',入栈;
    • 若为')',把栈顶符号至 '(' 之间的符号依次出栈加入到后缀表达式,'('直接出栈不加入后缀表达式,')'不入栈也不加入后缀表达式;
    • 若为乘除加减,要入栈的运算符优先级大于栈顶运算符的优先级,直接入栈,否则(小于等于),栈顶运算符出栈加入到后缀表达式,再次比较,重复上述过程,直到出现优先级小于自己的运算符成为栈顶,自己再入栈;

    4)中缀表达式为空时,栈中符号依次出栈加入到后缀表达式,直到栈为空

    vector<string> toRPN(string s)
    {
        vector<string> RPN;
        stack<string> sta;
        int n = s.size();
        for (int i = 0; i < n; ++i)
        {
            if (s[i] >= '0' && s[i] <= '9')
            {
                long long num = 0;//long long防止越int界
                while (i < n && s[i] >= '0' && s[i] <= '9')
                    num = 10 * num + s[i++] - '0';
                --i;
                RPN.push_back(to_string(num));
            }
            else if (s[i] == '+' || s[i] == '-')//加和减优先级比较低
            {
                while (!sta.empty() && (sta.top() == "*" || sta.top() == "/" || sta.top() == "+" || sta.top() == "-"))
                {
                    RPN.push_back(sta.top());
                    sta.pop();
                }
                s[i] == '+' ? sta.push("+") : sta.push("-");
            }
            else if (s[i] == '*' || s[i] == '/')
            {
                while (!sta.empty() && (sta.top() == "*" || sta.top() == "/"))
                {
                    RPN.push_back(sta.top());
                    sta.pop();
                }
                s[i] == '*' ? sta.push("*") : sta.push("/");
            }
            else if (s[i] == '(')
                sta.push("(");
            else if (s[i] == ')')
            {
                while (sta.top() != "(")
                {
                    RPN.push_back(sta.top());
                    sta.pop();
                }
                sta.pop();
            }
        }
        while (!sta.empty())//把栈中剩余的string全部写到RPN中
        {
            RPN.push_back(sta.top());
            sta.pop();
        }
        return RPN;
    }

    4.逆波兰表达式求值

    1)遇到数字就放入栈中

    2)遇到运算符operator就依次取出栈的上面两个元素a2,a1,然后a1 operator a2得出计算结果,再把计算结果放入栈中;

    3)遍历到表达式中的最后一个运算符operator时,把计算结果直接取出就是所求结果;

    4)注意一种特殊情况:一般的逆波兰表达式最后一个是运算符,但是如:{"18"},此时就应该直接取出;

    class Solution {
    public:
        int evalRPN(vector<string>& tokens)
        {
            if (tokens.size() == 1)//处理如{"18"}这种特殊情况
                return stoi(tokens[0]);
            stack<int> sta;
            int index = 0, res = 0;
            for (string str : tokens)
            {
                if (str != "+" && str != "-" && str != "*" && str != "/")
                    sta.push(stoi(str));
                else//遇到运算符
                {
                    int a2 = sta.top();
                    sta.pop();
                    int a1 = sta.top();
                    sta.pop();
                    if(str=="+")
                        sta.push(a1 + a2);
                    else if(str=="-")
                        sta.push(a1 - a2);
                    else if(str=="*")
                        sta.push(a1 * a2);
                    else if(str == "/")
                        sta.push(a1 / a2);
                }
            }
            return sta.top();
        }
    };

    5.前缀表达式

    1)前缀表达式又称波兰表达式,字符串中只有数字和运算符,没有括号,前缀表达式的运算符位于操作数之前

  • 相关阅读:
    Java 条件语句
    Java循环
    Java 变量
    Java 数据类型
    nginx+php发布网站
    安装MySQL5.7
    docker-compose参数
    部署
    dockerfile编写
    在VMware中安装CentOS7
  • 原文地址:https://www.cnblogs.com/Joezzz/p/9750130.html
Copyright © 2011-2022 走看看