栈的应用之算术表达式求值

栈是一种后进先出的数据结构。表达式求值是对栈的一个典型的应用。
对于如下一个表达式:

     1 + 2 * (3 + 4)

此算术表达式由一些操作符和操作数组成。其中,操作符有‘+’、‘*’、‘(’等,操作数有‘1’、‘2’、‘3’等。对于操作符来说,其运算是有优先级的。比如,上述表达式中,3+4应该先进行操作,将得到的结果再与2相乘。

算符间的优先关系如下:

运算符 + - * / #
+ > > < < < > >
- > > < < < > >
* > > > > < > >
/ > > > > < > >
< < < < < =
> > > > > >
# > > < < < =

根据算符间的优先关系表,使用两个栈。一个栈为OPTR,存储运算符,另一个栈OPND,存储运算数。
程序运行过程如下:

  1. 初始化,将两个栈均置为空。将‘#’提前入OPTR栈。
  2. 读取表达式的每个字符。若读取内容为运算数,则将其转换为整数后加入OPND栈。若读取内容为运算符,则比较所读运算符和栈顶运算符的优先级大小,做以下处理:
    若栈顶运算符优先级比较低,则将读取的运算符入OPTR栈,继续读取表达式的下一字符;
    若两个运算符优先级相等,则栈顶运算符直接出栈,继续读取表达式的下一字符;
    若栈顶运算符优先级比较高,则栈顶运算符出栈,同时,OPND栈出两个元素,将运算后的结果放入OPND栈中。

最后,OPND栈中只剩一个元素,即为表达式的值。

代码如下:

#include 
#include 

using namespace std;

stack<int> OPND;    //操作数
stack<char> OPTR;   //操作符
int priority[7][7] = {1,1,-1,-1,-1,1,1,1,1,-1,-1,-1,1,1,1,1,1,1,-1,1,1,1,1,1,1,-1,1,1,-1,-1,-1,-1,-1,0,-2,1,1,1,1,-2,1,1,-1,-1,-1,-1,-1,-2,0};    //存储优先级关系


void Initial();    //初始化
void GetExpressionValue();          //计算表达式的值
int GetPriority(char a, char b);    //得到a,b优先级
int Operate(int a, char theta, int b);    //计算a theta b的值

int main()
{
    int sum = 0;
    Initial();                   //初始化
    GetExpressionValue();        //计算表达式的值
    cout << OPND.top() << endl;
    return 0;
}

void Initial()
{
    //初始化,清空两个栈,并将‘#’放入操作符栈中
    while(!OPND.empty())
    {
        OPND.pop();
    }
    while(!OPTR.empty())
    {
        OPTR.pop();
    }
    OPTR.push('#');
}

void GetExpressionValue()
{
    int data[12] = {0};    //操作数
    int d = 0;
    char ch;
    char theta;
    int a = 0;
    int b = 0;
    int i = 0;
    int j = 0;
    cin >> ch;
    while(ch != '#' || OPTR.top() != '#')    //两个都=‘#’,求值结束
    {
        if(isdigit(ch))    //ch是操作数
        {
            i = 0;
            d = 0;
            while(isdigit(ch))      //将字符型的操作数转换为整型
            {
                data[i++] = ch - '0';
                cin>>ch;
            }
            for(j = 0; j < i; j++)
            {
                d = d + data[j]*pow(10.0, j);
            }
            OPND.push(d);           //操作数入栈
        }
        else               //ch是操作符
        {
            switch(GetPriority(OPTR.top(), ch))
            {
            case -1:        //栈顶的操作符优先级小于当前操作符
                {
                    OPTR.push(ch);
                    cin>>ch;
                    break;
                }
            case 0:         //相等,消去括号
                {
                    OPTR.pop();
                    cin>>ch;
                    break;
                }
            case 1:         //栈顶的操作符优先级大于当前操作符
                {
                    theta = OPTR.top();
                    OPTR.pop();
                    a = OPND.top();
                    OPND.pop();
                    b = OPND.top();
                    OPND.pop();
                    OPND.push(Operate(b,theta,a));    //将操作后的结果放入运算数栈中
                    break;
                }
            default:
                break;
            }
        }
    }
}

int GetPriority(char a, char b)
{
    int i = -1;
    int j = -1;
    switch(a)
    {
        case '#':
            i++;
        case ')':
            i++;
        case '(':
            i++;
        case '/':
            i++;
        case '*':
            i++;
        case '-':
            i++;
        case '+':
            i++;
        default:
            break;
    }

    switch(b)
    {
        case '#':
            j++;
        case ')':
            j++;
        case '(':
            j++;
        case '/':
            j++;
        case '*':
            j++;
        case '-':
            j++;
        case '+':
            j++;
        default:
            break;
    }

    if(i >= 0 && j >= 0)
    {
        return priority[i][j];
    }
    else
    {
        return -2;
    }
}

int Operate(int a, char theta, int b)
{
    int res = 0;
    switch (theta)
    {
    case '+':
        res = a + b;
        break;
    case '-':
        res = a - b;
        break;
    case '*':
        res = a * b;
        break;
    case '/':
        res = a / b;
        break;
    default:
        break;
    }
    return res;
}

你可能感兴趣的:(数据结构与算法)