Simple application of stack (using Stack to perform four mixed arithmetic operations) (JAVA)

Table of contents

Convert infix expression to postfix expression

Illustration

Code implementation process:

Complete code: 

Evaluate using postfix expressions:

Complete code:


 

First we need to understand the reverse Polish expression .

Convert infix expression to postfix expression

The so-called infix expression is actually what we usually write , for example: 3+4\times (2+ 2)+2\div 2; and its suffix expression (also called a reverse Polish expression) is 3\; 4\; 2\; 2+ \times + 2\; 2 \;\div + ;

Postfix expression: It means that it does not contain parentheses , and the operator is placed after the two operands . All calculations are performed strictly from left to right in the order in which the operators appear( the precedence rules of operators are no longer considered ).

If we want to use the program to perform the four mixed operations, the most important thing is to convert the input infix expression into a postfix expression .

First, let's assume that the operators only include addition, subtraction, multiplication, division and parentheses. Otherwise, the program will be too complicated (actually I can't write [cry]).

Illustration

Code implementation process:

First, we write a method whose return value is a dynamic string array (for easy calculation later), and the formal parameter is of string type (because the input value not only has numbers but also operators). The stack will be used here, so we also define a stack.

    public ArrayList<String> midChangeEng(String str) {
        //这里用动态数组就不用担心不够用
        ArrayList<String> ret = new ArrayList<String>();
        Stack<Character> stack = new Stack<>();
    }

At this time, create a new method to determine whether the incoming character is an operator. 

    public boolean isOperator(char s) {
        if (s == '+' || s == '-' || s == '*' || s == '/' || s == '(' || s == ')') {
            return true;
        }
        return false;
    }

We then use the position of the operator in the ASCII code to create an array to represent their priority.

int[] able = {1,0,0,0,0,1};//分别代表 * + (null) - (null) / 的优先级 

 Loop through strings

        //遍历字符串
        for (int i = 0; i < str.length(); i++) {
            char a = str.charAt(i);
            String tmp = "";//用来暂时存储出栈的数字
            if (isOperator(a)) {
                //是操作数
            }else{
                //如果是数字就放到ret中
            }
        }

        return ret;

For the operation of operands, there are too many repeated codes in this code, so it can be encapsulated into a method.

            if (isOperator(a)) {
                //是操作数
                switch (a) {
                    case '+'://判断如果优先级不大于栈顶的元素那么就先出栈在入栈
                        if(!stack.isEmpty()) {//出栈
                            while(!stack.isEmpty() && stack.peek() != '(' && able[(int)stack.peek() - 42] >= able[(int)a-42]) {
                                String b = "";
                                b += stack.pop();
                                ret.add(b);
                            }
                        }
                        stack.push(a);
                        break;
                    case '-':
                        if(!stack.isEmpty()) {//出栈
                            while(!stack.isEmpty() && stack.peek() != '(' && able[(int)stack.peek() - 42] >= able[(int)a-42]) {
                                String b = "";
                                b += stack.pop();
                                ret.add(b);
                            }
                        }
                        stack.push(a);
                        break;
                    case '*':
                        if(!stack.isEmpty()) {//出栈
                            while(!stack.isEmpty() && stack.peek() != '(' && able[(int)stack.peek() - 42] >= able[(int)a-42]) {
                                String b = "";
                                b += stack.pop();
                                ret.add(b);
                            }
                        }
                        stack.push(a);
                        break;
                    case '/':
                        if(!stack.isEmpty()) {//出栈
                            while(!stack.isEmpty() && stack.peek() != '(' && able[(int)stack.peek() - 42] >= able[(int)a-42]) {
                                String b = "";
                                b += stack.pop();
                                ret.add(b);
                            }
                        }
                        stack.push(a);
                        break;
                    case '(':
                        stack.push(a);
                        break;
                    case ')':
                        while(!stack.isEmpty() && stack.peek() != '(') {
                            String b = "";
                            b += stack.pop();
                            ret.add(b);
                        }
                        stack.pop();//删除‘(’
                        break;
                }

            }

 If it is a number, do the following

            else{
                //如果是数字就放到ret中
                String tmp = "";
                while(i < str.length() && !isOperator(str.charAt(i))) {//数字有可能是多位的
                    tmp += str.charAt(i);
                    i++;
                }
                i--;
                ret.add(tmp);
            }

Before exiting the function, you must first export everything in the stack.

        //将栈里面剩余的全部出栈
        while(!stack.isEmpty()) {
            String b = "";
            b += stack.pop();
            ret.add(b);
        }
        return ret;

Complete code: 

    public static ArrayList<String> midChangeEng(String str) {
        //这里用动态数组就不用担心不够用
        ArrayList<String> ret = new ArrayList<String>();
        Stack<Character> stack = new Stack<>();

        int[] able = {1,0,0,0,0,1};//分别代表 * + (null) - (null) / 的优先级
        //遍历字符串
        for (int i = 0; i < str.length(); i++) {
            char a = str.charAt(i);

            if (isOperator(a)) {
                //是操作数
                switch (a) {
                    case '+'://判断如果优先级不大于栈顶的元素那么就先出栈在入栈
                        abcd(ret, stack, able, a);
                        break;
                    case '-':
                        abcd(ret, stack, able, a);
                        break;
                    case '*':
                        abcd(ret, stack, able, a);
                        break;
                    case '/':
                        abcd(ret, stack, able, a);
                        break;
                    case '(':
                        stack.push(a);
                        break;
                    case ')':
                        while(!stack.isEmpty() && stack.peek() != '(') {
                            String b = "";
                            b += stack.pop();
                            ret.add(b);
                        }
                        stack.pop();//删除‘(’
                        break;
                }
            }else{
                //如果是数字就放到ret中
                String tmp = "";
                while(i < str.length() && !isOperator(str.charAt(i))) {//数字有可能是多位的
                    tmp += str.charAt(i);
                    i++;
                }
                i--;
                ret.add(tmp);
            }
        }
        //将栈里面剩余的全部出栈
        while(!stack.isEmpty()) {
            String b = "";
            b += stack.pop();
            ret.add(b);
        }
        return ret;
    }

Evaluate using postfix expressions:

This part is relatively simple , so I will show it directly.

Complete code:

        public int evalRPN(String[] tokens) {
            Stack<Integer> stack = new Stack<>();
            for (int i = 0; i < tokens.length; i++) {
                if (isOperator(tokens[i])) {
                    int num2 = stack.pop();
                    int num1 = stack.pop();
                    switch(tokens[i].charAt(0)) {
                        case '+':
                            stack.push(num1 + num2);
                            break;
                        case '-':
                            stack.push(num1 - num2);
                            break;
                        case '*':
                            stack.push(num1 * num2);
                            break;
                        case '/':
                            stack.push(num1 / num2);
                            break;
                    }
                }else {
                    stack.push(Integer.parseInt(tokens[i]));
                }
            }
            return stack.pop();
        }


        public boolean isOperator(String str) {
            if (str.length() != 1) {
                return false;
            }
            if (str.charAt(0) == '+' || str.charAt(0) == '-' || str.charAt(0) == '*' || str.charAt(0) == '/') {
                return true;
            }
            return false;
        }

Guess you like

Origin blog.csdn.net/2302_76339343/article/details/133177034