• 中缀表达式->后缀表达式


    中缀表达式:之前我们接触过的那种操作数+操作符+操作数形式的表达式

    后缀表达式:不包含括号,运算符放在两个运算对象的后面,所有的计算按运算符出现的顺序,严格从左向右进行(不再考虑运算符的优先规则,如:(2 + 1) * 3 , 即2 1 + 3 *

    中缀表达式转换成后缀表达式的代码:

    void postfix(char e[],char f[])//e是中缀表达式 f是后缀表达式。
    {
    int i = 0,top = 0,j = 0;
    char opst[100];
    top = 0;
    opst[top] = '#';
    top++;
    while(e[i] != '#')
    {
    if((e[i] >= '0' && e[i] <= '9') || e[i] = '.')
    f[j++] = e[i++];
    else if(e[i] == '0')
    i++;
    else if(e[i] == '(')
    {
    opst[top++] = e[i];
    }
    else if(e[i] == ')')
    {
    t = top - 1;
    while(opst[t] != '(')
    {
    f[j++] = opst[--top];
    t = top - 1;//即如果出现了(则 ()中的都应该运算玩,当然之前已经按()中e[i]的优先级先走了一部分了,现在只是
    //再走一些优先级比较低的。
    //其作用其实和最后的while循环本质是一样的,这里是对()内部进行最后的处理,while()那里是对整个表达式进行
    //最后的清底。
    }

    }
    else if(is_operation[i])
    {
    f[j++] = ' ';//用空格分开2个操作数,因为如2*3当读完一个操作数后,才会读到操作符,如果遇到操作符,就加空格的话
    //则下一个操作数和上一个操作数就隔开一个空格。
    while(priority(opst[top - 1]) >= priority[e[i]])
    f[j++] = opst[--top];//当刚读取的操作符小于等于桟顶的操作符 则把桟中的操作符赋值到后缀表达式中。

    opst[top++] = e[i++];//当读取的操作符大于桟的操作符时 则把该读取的操作符进桟。
    //因为opst[0]是优先级最低的‘#’故一定会执行进桟操作。
    }

    }
    while(top)//中缀表达式全部读完后,操作符桟还有操作费的话。
    f[j++] = opst[--top];

    }


    /*思路:如3+5*2 先读2个数,+压入桟 无法一开始就放到后缀表达式中,因为不知道其是否要先运算。然后当3 5的运算符不确定能不能先
    运算时,再读下一个数字2,再读5和2的运算符* 大于之前桟顶的+ 则入桟。因为最后读完整个中缀表达式时,需要把操作符桟出桟,所以
    在这里可以看出操作符桟优先级是从小到大排列的,按桟的规律,优先级大的先出。满足后缀表达式的思路。

    更深层次的理解:根据后缀表达式的运算法则,2个数字再加一个符号就可以运算。而中缀是操作数 操作符 操作数才能运算,故他们之间
    的转换可以这样看:先从中缀中读2个操作数,因为这是基本运算必须的,在这中间把2操作数的操作符放到一个桟中,然后读取第3个操作数,
    此时,第三个操作数和第二个操作数又成可以运算状态,在其之间又有一个操作符,这个操作符是否入桟要看其优先级,如果低于等于之前的
    桟顶的操作符,就把桟中的操作符放到后缀表达式. 如果刚读取的操作符优先级大于栈顶的操作符,则可以把刚读取的符号入桟.(因为在3个
    操作数和2个操作符的体统里面,无论其外是什么形式,都可以先判断这2个操作符的优先级,当这个操作符先出现且其优先级更高,显然我们
    就可以让他写到后缀表达式了,因为他可以先运算,因为他肯定要比优先级他低且在他后面出现的那个操作符先运算。但如果优先级更高的
    那个操作符在后面,则不能先运算了,因为有可能在这个形式外面还有更高的优先级,故这2个操作符都会入桟,以优先级从低到高的顺序排列,
    再和后面的操作符比较,如此往复。这里的最难想到的就是,一旦一个操作符他比他后面的那个操作符优先级高的话,无论其他什么情况都可先
    运算他两边的操作数。)
    */

    辅助代码:


    int is_operation(char op)//判断一个字符是否为运算符。
    {
    switch(op)
    {
    case '+';
    case '-';
    case '*';
    case '/';
    return 1;
    default:return 0;
    }
    }

    int priority(char op)//求操作符的的优先级。
    {
    switch(op)
    {

    case '#':return -1;
    case '(':return 0;
    case '+':
    case '-':return 1;
    case '*':
    case '/': return 2;
    default: return -1;

    }
    }

  • 相关阅读:
    2021年通达信指标公式大全,值得收藏!
    网络兼职?威客?为什么我会觉得网络兼职,威客会是人生中应该具备的一种能力!
    SeMusic 音乐网站源代码,PHP音乐系统,人人都是站长人人都可副业创业!
    JavaScript 查看图片,带缩放放大效果
    JS (javascript) 计算循环当前时间,javascript 时间钟表
    关键词被冷藏?关键词没排名?任务网站长们该何去何从?
    关键词任务网被K,对于任务网该何去何从?我认为任务网存活只有一条出路!
    C3属性的轮播图(持续更新)
    自己写的文字轮播(简陋版)
    带锁的3D切割轮播图
  • 原文地址:https://www.cnblogs.com/aloney/p/4831327.html
Copyright © 2020-2023  润新知