Leetcode 224. 基本计算器

实现一个基本的计算器来计算一个简单的字符串表达式的值。

字符串表达式可以包含左括号 ( ,右括号 ),加号 + ,减号 -,非负整数和空格  。

示例 1:

输入: "1 + 1"
输出: 2
示例 2:

输入: " 2-1 + 2 "
输出: 3
示例 3:

输入: "(1+(4+5+2)-3)+(6+8)"
输出: 23
说明:

你可以假设所给定的表达式都是有效的。
请不要使用内置的库函数 eval。

链接:https://leetcode-cn.com/problems/basic-calculator
思路:双栈

解法一经过了一个中间过程,先转为了后缀表达式然后进行求值。我们其实可以直接利用两个栈,边遍历边进行的,这个方法是我当时上课学的方法。从 这里 把过程贴到下边,和解法一其实有些类似的。

使用两个栈,stack0 用于存储操作数,stack1 用于存储操作符
从左往右扫描,遇到操作数入栈 stack0
遇到操作符时,如果当前优先级低于或等于栈顶操作符优先级,则从 stack0 弹出两个元素,从 stack1 弹出一个操作符,进行计算,将结果并压入stack0,继续与栈顶操作符的比较优先级。
如果遇到操作符高于栈顶操作符优先级,则直接入栈 stack1
遇到左括号,直接入栈 stack1。
遇到右括号,则从 stack0 弹出两个元素,从 stack1 弹出一个操作符进行计算,并将结果加入到 stack0 中,重复这步直到遇到左括号

以上来自 leetcode题解

自己的想法:都在代码里面

class Solution {
   public int calculate(String s) {
    
    //先将所有的
        char[] array=s.toCharArray();
//        System.out.println(array);
//        System.out.println(array[0]);
        //定义数字栈 符号栈
        Stack<Integer> num=new Stack<>();
        Stack<Character> op =new Stack<>();
        int n= array.length;
//        System.out.println(n);
        int is_calculate=-1;//定义是否能计算
        int temp_num=-1;
//        System.out.println(isOperation("+"));
        // char c='+';
        // String ak=c+"";
        // System.out.println(ak);

        for(int i=0;i<n;i++)//循环遍历
        {
            if(array[i]==' ')//如果是空格 则进行
            {
                continue;
            }


            if(isNumber(array[i]))//如果是数字的话
            {
                if(temp_num==-1)
                {//如果前面没有遇到过数字
                    temp_num=array[i]-'0';
                }else
                {
                //如果前面遇到了数字了 那就是要将前面的*10在加上现在的temp
                    temp_num=temp_num*10+(array[i]-'0');
                }
            }else//遇到的不是数字 是操作符或者括号 先将之前的数字进堆栈(所以是遇到了符号才会压入堆栈)
            {
                if(temp_num!=-1)
                {
                    num.push(temp_num);//压到堆栈中
                    temp_num=-1;//然后等下一个数字
                }
                //判断了不是空格 不是数字之后 是判断操作符号
                if(isOperation(array[i]))
                {
                    //如果是操作符号的话
                    while (!op.isEmpty())
                    {
                        //只要操作符zhan不为空 或者遇到了左括号 就一直运算到最后
                        if(op.peek()=='(')
                        {
                            break;
                        }

                        int num1=num.pop();
                        int num2=num.pop();

                        if (op.pop()=='+')
                        {
                            num.push(num1+num2);
                        }else//如果是减号
                        {
                            num.push(num2-num1);
                        }
                    }
                    //前面的运算符计算完之后 将这个运算符入栈
                    op.push(array[i]);
                }
                else//遇到的不是数字 也不是操作符号 那只有左右括号了
                {
                    if(array[i]=='(')
                    {//如果是左括号 直接入栈
                        op.push(array[i]);
                    }

                    if (array[i]==')')
                    {
                        //如果遇到了右边的括号 那直接进行一个运算 直到遇见(,其实这边也就一个运算符 因为之前的都被算过了
                        while (op.peek()!='(')
                        {
                            int num1=num.pop();
                            int num2=num.pop();

                            if (op.pop()=='+')
                            {
                                num.push(num1+num2);
                            }else//如果是减号
                            {
                                num.push(num2-num1);
                            }
                        }
                        //括号内计算完之后 将左括号出站 右括号从来没进过站 所以不用出站
                        op.pop();
                    }
                }
            }

        }
        //(由于是遇到了符号才会压入堆栈)考虑到有些只有一个运算符号的情况 比如 1+1 这时候没有遇到下一个运算符 那之前的就没有办法运算了
        if(temp_num!=-1)
        {
            num.push(temp_num);
        }
//        System.out.println(num.size());
        while (!op.isEmpty()) {
            int num1 = num.pop();
            int num2 = num.pop();
            if (op.pop() == '+') {
                num.push(num1 + num2);
            } else {
                num.push(num2 - num1);
            }
        }
    return num.pop();
}

private boolean isNumber(char c) {
    return c >= '0' && c <= '9';
}

 private static boolean isOperation(char t) {
        return t=='+' || t=='-' || t=='*' || t=='/';
    }
}
原文地址:https://www.cnblogs.com/William-xh/p/13799043.html