栈实现四则运算

该博客介绍了如何将中缀表达式转换为后缀表达式,并通过栈来计算后缀表达式的结果。首先,通过初始化字符串处理连续数字的运算,然后利用栈来处理运算符的优先级,将中缀表达式转化为后缀表达式。接着,再次使用栈对后缀表达式进行计算,得到最终的结果。整个过程涉及到了栈的数据结构和运算符优先级的判断。
摘要由CSDN通过智能技术生成

栈的特点:先进后出

中缀表达式转后缀表达式

申请一个栈对象:用于存放符号(运算符和括号)

创建一个StringBuffer对象:用于保存数字

实现过程:输入的计算表达式为一个字符串,获取字符串中每一个下标的字符,若获取到的字符为数字则存放在StringBuffer对象中,若为运算符或括号则进行入栈。当入栈的符号为右括号时,则停止入栈,把左括号之前的运算进行出栈操作并保存在StringBuffer对象中,然后把左括号进行出栈操作。

 计算后缀表达式

申请一个栈对象:用于存放数字

实现过程:把后缀表达式进行入栈操作,入栈过程中若遇到运算符,则获取栈中的栈顶元素和下一个元素,进行相关运算操作,再把运算所得的结果进行入栈,依次进行直到后缀表达式入栈结束,此时栈中就剩余一个元素,该元素就是计算表达式的结果。

主要解决问题

运算符优先级的判断

处理大于两个连续的数字的拼接

代码实现

//初始化字符串
    public static List InitData(String str) {
        //把字符串存放在集合中,主要解决数字为两位数字以上时的运算
        List<String> list=new ArrayList<>();
        //存放遇到运算符之前的数字
        StringBuffer stringBuffer=new StringBuffer();
        for (int i = 0; i < str.length(); i++) {
            //当前字符为运算符
            if(str.charAt(i)=='+'||str.charAt(i)=='-'||str.charAt(i)=='*'||str.charAt(i)=='/'||str.charAt(i)==')'||str.charAt(i)=='('){
                if (stringBuffer.length()>0){
                    //把运算符之前的数字添加到集合中
                    list.add(stringBuffer+"");
                    //清空stringBuffer的数据,为了存放下一个数字
                    stringBuffer.setLength(0);
                }
                //把当前运算符添加到集合中
                list.add(str.charAt(i)+"");
            }else{
                //数字直接添加到  stringBuffer
                stringBuffer.append(str.charAt(i));
            }
        }
        //把最后一个数字添加到集合中
        if (stringBuffer.length()>0){
            list.add(stringBuffer+"");
        }
        return list;
    }
    //中缀转后缀
    public static List<String> DealData(String str){
        //接收初始化后的数据list
        List<String> list=InitData(str);
        //存放后缀表达式
        List<String>list1=new ArrayList();
        //判断运算符的优先级
        Map<String,Integer> map =new HashMap<>();
        map.put("+",1);
        map.put("-",1);
        map.put("*",2);
        map.put("/",2);
        map.put("(",3);
        map.put(")",3);
        //存放运算符
        Stack<String> stack=new Stack<>();
        for (int i = 0; i < list.size(); i++) {
            //遇到左括号直接入栈
            if (list.get(i).equals("(")){
                stack.push(list.get(i));
            } else if (list.get(i).equals(")")){//遇到右括号时把栈里面左括号之前的运算符添加到集合中
                while(!stack.peek().equals("(")){
                   list1.add(stack.pop());
                }
                //删除左括号
                stack.pop();
                //遇到运算符
            }else if (list.get(i).equals("+")||list.get(i).equals("-")||list.get(i).equals("/")||list.get(i).equals("*")){
                if (stack.isEmpty()){
                    //栈空直接进栈
                    stack.push(list.get(i));
                }else {
                        int  temp1=map.get(list.get(i));
                        int  temp2=map.get(stack.peek());
                        //当前运算符的优先级比栈顶运算符的优先级低,并且栈顶元素不能等于左括号
                        if (temp1<temp2 &&(!stack.peek().equals("("))) {
                            while(!stack.isEmpty()){
                                //栈顶元素出栈
                                list1.add(stack.peek());stack.pop();
                            }
                            //把当前字符入栈
                            stack.push(list.get(i));
                        } else {
                            //当前运算符的优先级比栈顶运算符的优先级高
                            stack.push(list.get(i));
                        }
                }
            }else {
                //数字直接添加到集合中
                list1.add(list.get(i));
            }
        }
        //添加集合中剩余的数据
       while(!stack.isEmpty()){
           list1.add(stack.pop());
        }
        return   list1;
    }
    //后缀计算结果
    public static BigDecimal Calculator(String str){
        //接收中缀转成的后缀
       List<String> list=DealData(str);
       //存数字
        Stack<BigDecimal> stack=new Stack<>();
        for (int i = 0; i < list.size(); i++) {
            //遇到运算符
           if (list.get(i).equals("+")||list.get(i).equals("-")||list.get(i).equals("/")||list.get(i).equals("*")){
              //把运算符之前的两个数字取出
               BigDecimal i1=stack.peek();stack.pop();
               BigDecimal i2=stack.peek();stack.pop();
               //接收i1、i2计算的结果
               BigDecimal sum;
               if (list.get(i).equals("-")){
                   sum=i2.subtract(i1);
               }else if (list.get(i).equals("+")){
                   sum=i2.add(i1);
               }else if (list.get(i).equals("*")){
                   sum=i2.multiply(i1);
               }else {
                   //处理无限循环的结果
                   sum= BigDecimal.valueOf(i2.divide(i1,3, BigDecimal.ROUND_DOWN).doubleValue());
               }
               stack.push(sum);
           }else {//数字直接进栈
               stack.push(new BigDecimal(list.get(i)));
           }
        }
        //获取栈中的最后一个数字,即就是运算结果
        BigDecimal result =stack.peek();
        return result;
    }

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值