利用栈和后缀表达式计算后缀表达式

版权声明:本文为博主原创文章,未经博主允许不得转载。 https://blog.csdn.net/qq_30986521/article/details/82907779

原理不赘述,随便找个博客看看后缀表达式即其计算

原理简单,实现起来有几个小问题:

Q1:A+B*C的后缀变表达式为ABC*+,当ABC为具体的1、2、3时,后缀表达式为123*+, 123怎么理解,1和2和3还是12和3还是1和23...

A1:用||间隔数字,如|1||2||3|*+就很明确了。

Q2:输入是字符串,计算要int/double

A2:所以需要自己写一个一个字符串转换为int/double的函数,目前写的字符串转换成int,毕竟double不精确,如果想用double,可以自己实现一个分数类,重载各种运算符即可,要精确结果,用分数表示,要小数结果,分子除以分母

Q3:如何拓展其他云算法

A3:实现一个add_operation即可,并提供计算方法,优先级信息

C++ class封装实现

#include <iostream>
#include <string>
#include <vector>

using namespace std;


//简单的函数直接写成内联的了
class caculator
{
public:
    caculator()
    {
        initial_priority();
    }
    ~caculator()
    {
        
    }
    int add_operation(char op, int priority, int(*func)(const int, const int))
    {
        int status = 0;
        if (this->priority[op] == 0)
        {
            this->priority[op] = priority;
            this->op_func[op] = func;
            status = 1;
        }
        return status;
    }
    
    int get_result(string s);
    
private:
    int priority[128];
    int (*op_func[128])(const int, const int);
    static int get_num(string formula, int &index);
    void initial_priority();
    string get_postfix(string formula);
};
//主要的功能函数
//初始化运算符优先级信息
void caculator::initial_priority()
{
    op_func['+'] = op1;
    op_func['-'] = op2;
    op_func['*'] = op3;
    op_func['/'] = op4;
    
    priority['+'] = 2;
    priority['-'] = 2;
    priority['*'] = 3;
    priority['/'] = 4;
    priority['('] = 1;
}
//string->int
int caculator::get_num(string formula, int &index)
{
    int sum = 0;
    while (formula[index] >= '0' && formula[index] <= '9')
    {
        sum = sum * 10 + formula[index] - '0';
        index++;
    }
    return sum;
}
//中缀表达式变后缀表达式
string caculator::get_postfix(string formula)
{
    string post = "";
    vector<int> num;
    vector<char> op;

    for (int i = 0; i < formula.length(); i++)
    {
        char c = formula[i];
        if (c == ' ') continue;
        if (isdigit(c))
        {
            
            int var = get_num(formula, i);
            post += (string("|") + to_string(var) + string("|"));
        }
        c = formula[i];
        if (!isdigit(c))
        {
            if (c == '(')
            {
                op.push_back(c);
            }
            else if (c == ')')
            {
                while (op.back() != '(')
                {
                    post += op.back();
                    op.pop_back();
                }
                op.pop_back();
            }
            else
            {
                while (op.size() > 0 && priority[op.back()] >= priority[c])
                {
                    post += op.back();
                    op.pop_back();
                }
                op.push_back(c);
            }
        }
    }
    
    while (op.size() != 0)
    {
        post += op.back();
        op.pop_back();
    }
    
    return post;
}
//计算
int caculator::get_result(string s)
{
    vector<int> num;
    string postfix = get_postfix(s);
    int x, y;
    
    for (int i = 0; i < postfix.length(); i++)
    {
        char c = postfix[i];
        if (c == '\0') continue;
        if (c != '|' && isdigit(c))
        {
            x = get_num(postfix, i);
            num.push_back(x);
        }
        c = postfix[i];
        if (c != '|' && !isdigit(c))
        {
            x = num.back();
            num.pop_back();
            y = num.back();
            num.pop_back();
            num.push_back(op_func[c](y, x));
        }
    }
    return num[0];
}
//main
int main()
{
    caculator c;
    
    cout << c.get_result("1+2*(3+4/2)") << endl;
    
    return 0;
}

随便写写,可能有bug,并没有仔细debug

猜你喜欢

转载自blog.csdn.net/qq_30986521/article/details/82907779