天天看點

java實作計算表達式

java實作計算表達式

列入計算:5+2*(6*(2+4))+7

思路:把數字和操作字元裝入2個棧中,根據操作字元的優先級計算,最後數中留下計算結果。

java實作計算表達式

上代碼:

import java.util.Stack;

public class Calculation {
    private Stack<Character> chars;
    private Stack<Long> numbers;

    public long cal(String biaodashi) {
        biaodashi = biaodashi == null ? "" : "=".equals(biaodashi.charAt(biaodashi.length() - 1)) ? biaodashi : biaodashi + "=";//+ =
        Stack<Character> kuohao = new Stack<>(); //校驗  ()比對
        for (int i = 0; i < biaodashi.length(); i++) {
            char c = biaodashi.charAt(i);
            if (!(isNumber(c)
                    || "+".equals(c + "")
                    || "-".equals(c + "")
                    || "*".equals(c + "")
                    || "/".equals(c + "")
                    || "=".equals(c + "")
                    || "(".equals(c + "")
                    || ")".equals(c + ""))) {
                System.err.println("表達式錯誤");
                return -1;         //結束程式
            }
            if ("(".equals(c + "")) {
                kuohao.push(new Character(c));
            }
            if (")".equals(c + "")) {
                if (kuohao.empty() || !"(".equals(kuohao.pop() + "")) {
                    System.out.println("括号不比對");
                    return -1;
                }
            }
        }
        if (!kuohao.isEmpty()) {
            System.out.println("右括号少了");
            return -1;
        }
        chars = new Stack<>(); //使用的時候建立
        numbers = new Stack<>(); //優化記憶體
        StringBuffer stringBuffer = new StringBuffer(); //緩存多位操作數
        //計算
        for (int i = 0; i < biaodashi.length(); i++) {
            char c = biaodashi.charAt(i);
            if (isNumber(c)) {
                stringBuffer.append(c);
            } else {
                //加入數字
                if (!"".equals(stringBuffer.toString())) {
                    numbers.push(Long.parseLong(stringBuffer.toString()));
                    stringBuffer = new StringBuffer();
                }
                //棧頂有符号  且c的優先級小于等于棧頂的優先級 一直計算
                while (!chars.isEmpty() && xiaoyu(c)) {
                    Long after = numbers.pop();
                    Long before = numbers.pop();
                    char operation = chars.pop();
                    switch (operation) {
                        case '+':
                            numbers.push(before + after);
                            break;
                        case '-':
                            numbers.push(before - after);
                            break;
                        case '*':
                            numbers.push(before * after);
                            break;
                        case '/':
                            numbers.push(before / after);
                            break;
                    }
                }   //while 結束
                //添加符号 如果為) 去除()
                if (!"=".equals(c + "")) {
                    chars.push(new Character(c));
                    if (")".equals(c + "")) {
                        chars.pop();
                        chars.pop();
                    }
                }
            } //else 結束
        }//for 結束
        return numbers.pop();   //傳回計算結果
    }

    private boolean xiaoyu(char c) {
        if ("(".equals(chars.peek() + ""))
            return false;     //c 需要入符号棧
        char peek = chars.peek();

        switch (c) {
            case '+':
            case '=':
            case '-':
            case ')':
                return true;    //不入棧 去計算
            case '*':
            case '/': {
                if (peek == '+' || peek == '-')
                    return false;
                return true;
            }
            case '(':
                return false;
        }

        return false;
    }

    public boolean isNumber(Character number) {
        if (number <= 57 && number >= 48)
            return true;
        return false;
    }

    public static void main(String[] args) {
        String num = "5+2*(6*(2+4))+7"; // 預設的算式
        long cal = new Calculation().cal(num);
        System.out.println(cal);
    }
}
           

隻要敢嘗試去寫去思考就一定離結果越近,希望你我共同進步!

參考位址

https://www.cnblogs.com/wuqianling/p/5671667.html