题解 | #表达式求值#
https://www.nowcoder.com/practice/9566499a2e1546c0a257e885dfdbf30d
使用逆波兰法
1、将表达式正确分割
make
2、将中缀表达式变成后缀表达式,便于计算
nibolan3、计算
import java.util.Stack; import java.util.Scanner; import java.util.ArrayList; /** * HJ54 表达式求值 - 简单 */ public class Main { public static void main(String[] args) { Scanner in = new Scanner(System.in); calcat(in); in.close(); } /** * 1+((2+3)*4)-5 *-1*(-1-1) * @param cs * @return */ private static String[] nibolan(String[] cs) { Stack<String> s1 = new Stack<>(); ArrayList<String> ss = new ArrayList<>(); for (int i = 0; i < cs.length; i++) { String temss = cs[i]; if (temss.matches("-?\\d+")) { // 如果是数字 ss.add(temss); } else if (temss.equals("(")) { s1.push(temss); } else if (temss.equals(")")) { // 如果是右括号 while (!s1.peek().equals("(")) { ss.add(s1.pop()); } s1.pop(); // 把对应的左括号弹出来。 } else { while (s1.size() != 0 && property(s1.peek().toCharArray()[0]) != 2 && property(s1.peek().toCharArray()[0]) >= property(temss.toCharArray()[0])) { ss.add(s1.pop()); } s1.push(temss); } } while (!s1.isEmpty()) { ss.add(s1.pop()); } return ss.toArray(new String[0]); } private static void calcat(Scanner in) { while (in.hasNext()) { String calc = in.nextLine(); calc = calc.replace(" ", ""); String[] cs = make(calc); cs = nibolan(cs); Stack<String> css = new Stack<>(); for (String temp : cs) { if (temp.matches("-?\\d+") && !temp.equals("-")) { css.push(temp); } else { int end = Integer.parseInt(css.pop()); int start = Integer.parseInt(css.pop()); int res = 0; if (temp.equals("+")) { res = start + end; } else if (temp.equals("-")) { res = start - end; } else if (temp.equals("/")) { res = start / end; } else if (temp.equals("*")) { res = start * end; } css.push(res + ""); } } System.out.println(css.pop()); } } private static String[] make(String calcString) { StringBuilder sb = new StringBuilder(); ArrayList<String> temps = new ArrayList<>(); char[] chars = calcString.toCharArray(); for (int i = 0; i < chars.length; i++) { if (Character.isDigit(chars[i])) { sb.append(chars[i]); } else { if (chars[i] == '-') { // 如果是减号,前面不是数字,或者没有字符,说明他也是数字的一部分,表示负数 if (i == 0 || chars[i - 1] == '(' || chars[i - 1] == '+' || chars[i - 1] == '-' || chars[i - 1] == '*' || chars[i - 1] == '/' ) { sb.append(chars[i]); } else { if (sb.length() != 0) { temps.add(sb.toString()); temps.add(String.valueOf(chars[i])); sb.setLength(0); } else { temps.add(String.valueOf(chars[i])); } } } else { if (sb.length() != 0) { temps.add(sb.toString()); temps.add(String.valueOf(chars[i])); sb.setLength(0); } else { temps.add(String.valueOf(chars[i])); } } } } if (sb.length() != 0) { temps.add(sb.toString()); sb.setLength(0); } return temps.toArray(new String[0]); } private static int calcc(int start, int end, String c) { if (c.equals("+")) { return start + end; } else if (c.equals("-")) { return start - end; } else if (c.equals("*")) { return start * end; } else if (c.equals("/")) { return start / end; } return 0; } private static int property(char c) { if (c == '*' || c == '/') { return 1; } else if (c == '+' || c == '-') { return 0; } else { return 2; } } }