表达式计算(中序转后序)

蓝桥杯: 算法训练 表达式计算

问题描述
  输入一个只包含加减乖除和括号的合法表达式,求表达式的值。其中除表示整除。
输入格式
  输入一行,包含一个表达式。
输出格式
  输出这个表达式的值。
样例输入
1-2+3*(4-5)
样例输出
-4
数据规模和约定
  表达式长度不超过100,表达式运算合法且运算过程都在int内进行。

package qiao;
import java.util.*;

//计算  2*(4+(88-86)/2)

class caculater{
    private String[] sArry;//存分割后的字符串
    private Stack<String> houx = new Stack<String>();
    private Stack<String> fuhao = new Stack<String>();

    //结构初始化
    caculater(String getin){
        int i = getin.length()-1;
        String temp = new String();
        int j = 0;
        Boolean bool = true;
        //在符号左右各添加一个#字符划分
        while(bool){
            if(i==j){
                bool = false;
            }
            if(getin.charAt(j)=='+'
             ||getin.charAt(j)=='-'
             ||getin.charAt(j)=='*'
             ||getin.charAt(j)=='/'
             ||getin.charAt(j)=='('
             ||getin.charAt(j)==')'){
                temp += '#';
                temp += getin.charAt(j);
                temp += '#';               //填完后是2#*##(#4#+##(#88#-#86#)##/#32#)#
            }else{  
                temp += getin.charAt(j); 
            }
            j++;
        }
        sArry = temp.split("#+");//用正则表达式分割成字符串,#+表示一个或多个#字符//结果:[2,*,(,4,+,(,88,-,85,),/,2,)]
    }

    //后序排列
    public void backsort(){
        //循环sArry
        for(int i= 0;i<sArry.length;i++){
            //如果不是字符,就直接push入houx栈
            if(!sArry[i].equals("+")
             &&!sArry[i].equals("-")
             &&!sArry[i].equals("*")
             &&!sArry[i].equals("/")
             &&!sArry[i].equals("(") 
             &&!sArry[i].equals(")")){
                houx.push(sArry[i]);
                continue;
            //否则是字符,若符号栈为空,直接入栈
            }else if(fuhao.isEmpty()){
                fuhao.push(sArry[i]);
                continue;
            //如果为(括号,直接入符号栈
            }else if(sArry[i].equals("(")){
                fuhao.push(sArry[i]);
                continue;
            //如果为)括号
            }else if(sArry[i].equals(")")){
                /**
                 * 不断出栈直到(括号出现
                 * 
                 */
                while(!fuhao.peek().equals("(")){
                    houx.push(fuhao.pop());
                }
                fuhao.pop();//清掉(括号
            //如果不为空,且要入的符号比符号栈顶的符号优先级高,则直接push入符号栈
            }else if(!fuhao.isEmpty()&&check(sArry[i],fuhao.peek())){            //
                fuhao.push(sArry[i]);
                continue;
            //否则,将符号栈内优先级高的符号出栈,push入houx栈,再将符号存进符号栈
            }else{
                houx.push(fuhao.pop());
                fuhao.push(sArry[i]);
                continue;
            }
        }
        //遍历完后,直接将符号栈内的依次出栈,push入houx栈
        while(!fuhao.isEmpty()){
            houx.push(fuhao.pop());
        }//结果是:2 4 88 86 - 2 / + *   栈内顺序
    }

    //check对比优先级
    private boolean check(String a,String b){
        //如果符号栈内是(括号,直接返true
        if(b.equals("(")){
            return true;
        }
        //如果符号栈内的优先级比要入的高,返回false
        if((b.equals("*")||b.equals("/"))&&(a.equals("+")||a.equals("-"))){         //b>a
            return false;
        }
        //。。。。。。。。。。。。。的低,返回true
        if((b.equals("+")||b.equals("-"))&&(a.equals("*")||a.equals("/"))){         //b<a
            return true;
        }
        return false;
    }
    //出栈计算
    public void suan(){

        backsort();//后序排列

        //结果栈end
        Stack<Integer> end = new Stack<Integer>();
        //遍历houx栈
        for(int i=0; i<houx.size();i++){
            //如果是加号,end pop出来两个数字,计算后结果入栈
            if(houx.get(i).equals("+")){
                int b = end.pop();
                int a = end.pop();
                end.push(a+b);
                continue;
            //如果是减号,end pop出栈两个数字,计算后结果入栈
            }else if(houx.get(i).equals("-")){
                int b = end.pop();
                int a = end.pop();
                end.push(a-b);
                continue;
            //如果是乘号,end pop出栈两个数字,计算后结果入栈
            }else if(houx.get(i).equals("*")){
                int b = end.pop();
                int a = end.pop();
                end.push(a*b);
                continue;
            //如果是除号,end pop出栈两个数字,计算后结果入栈   
            }else if(houx.get(i).equals("/")){
                int b = end.pop();
                int a = end.pop();
                end.push(a/b);
                continue;
            }else{
                //不是符号,也就是数字的情况,Integer.parseInt转int型, push入栈
                end.push(Integer.parseInt(houx.get(i)));
            }
        }

        //输出结果
        System.out.println(end.pop());
    }

}
public class BiaodashijisuanDemo {
    public static void main(String[] args) {
        Scanner sc = new Scanner(System.in);
        //获取输入
        String getin = sc.nextLine();
        //结构化
        caculater cl = new caculater(getin);
        //计算
        cl.suan();

        sc.close();
    }
}

看了一遍书后,按着自己的理解写了一遍。对比之前自己的渣渣写法要好到不知道哪里去了。
英语还是很蛋疼,变量名都是起的拼音(╥╯^╰╥)

  • 0
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值