Parse simple math expression
This task use java to parse simple math expression.
Parse simple math expression
- Create Formula class as following
- Call Formula.calculate() method as following
Call Formula.calculate() method
Formula class
1 | Map<String, Object> data = new HashMap<String, Object>(); |
2 | data.put("a", 2); |
3 | data.put("b", 3); |
4 | String formula = "a - b * a"; |
5 | Object result = Formula.calculate(data, formula); |
6 | if (result != null) { |
7 | logger.info(result.toString()); |
8 | } else { |
9 | logger.info("NULL"); |
10 | } |
Map<String, Object> data = new HashMap<String, Object>(); data.put("a", 2); data.put("b", 3); String formula = "a - b * a"; Object result = Formula.calculate(data, formula); if (result != null) { logger.info(result.toString()); } else { logger.info("NULL"); }
1 | public static class Formula { |
2 | |
3 | private Map<String, Object> data; |
4 | private String formula; |
5 | |
6 | public Formula(Map<String, Object> data, String formula) { |
7 | this.data = data; |
8 | this.formula = formula; |
9 | } |
10 | |
11 | public static Object calculate(Map<String, Object> data, String formula) { |
12 | return new Formula(data, formula).calculate(); |
13 | } |
14 | |
15 | public Object calculate() { |
16 | int pos = lastOperator(formula, new String[] { "+", "-" }); |
17 | if (pos < 0) { |
18 | pos = lastOperator(formula, new String[] { "*", "/" }); |
19 | if (pos < 0) { |
20 | return calculate(formula); |
21 | } else { |
22 | return calculate(formula.substring(0, pos).trim(), formula.charAt(pos) + "", formula.substring(pos + 1).trim()); |
23 | } |
24 | } else { |
25 | return calculate(formula.substring(0, pos).trim(), formula.charAt(pos) + "", formula.substring(pos + 1).trim()); |
26 | } |
27 | } |
28 | |
29 | private Object calculate(String leftSide, String operator, String rightSide) { |
30 | Object valLeft = null; |
31 | Object valRight = null; |
32 | int pos = lastOperator(leftSide, new String[] { "+", "-" }); |
33 | if (pos < 0) { |
34 | pos = lastOperator(leftSide, new String[] { "*", "/" }); |
35 | if (pos < 0) { |
36 | valLeft = calculate(leftSide); |
37 | } else { |
38 | valLeft = calculate(leftSide.substring(0, pos).trim(), leftSide.charAt(pos) + "", leftSide.substring(pos + 1).trim()); |
39 | } |
40 | } else { |
41 | valLeft = calculate(leftSide.substring(0, pos).trim(), leftSide.charAt(pos) + "", leftSide.substring(pos + 1).trim()); |
42 | } |
43 | pos = lastOperator(rightSide, new String[] { "*", "/" }); |
44 | if (pos < 0) { |
45 | valRight = calculate(rightSide); |
46 | } else { |
47 | valRight = calculate(rightSide.substring(0, pos).trim(), rightSide.charAt(pos) + "", rightSide.substring(pos + 1).trim()); |
48 | } |
49 | return calculate(valLeft, operator, valRight); |
50 | } |
51 | |
52 | private Object calculate(Object leftSide, String operator, Object rightSide) { |
53 | Object tag = null; |
54 | if (leftSide == null || rightSide == null) return null; |
55 | if (isNumber(leftSide) && isNumber(rightSide)) { |
56 | double valLeft = parseNumber(leftSide); |
57 | double valRight = parseNumber(rightSide); |
58 | tag = calculate(valLeft, operator, valRight); |
59 | } else if (isString(leftSide) || isString(rightSide)) { |
60 | if ("+".equals(operator)) { |
61 | tag = leftSide.toString() + rightSide.toString(); |
62 | } |
63 | } |
64 | return tag; |
65 | } |
66 | |
67 | private Object calculate(double leftSide, String operator, double rightSide) { |
68 | if ("+".equals(operator)) { |
69 | return leftSide + rightSide; |
70 | } else if ("-".equals(operator)) { |
71 | return leftSide - rightSide; |
72 | } else if ("*".equals(operator)) { |
73 | return leftSide * rightSide; |
74 | } else if ("/".equals(operator) && rightSide != 0) { |
75 | return leftSide / rightSide; |
76 | } else { |
77 | return null; |
78 | } |
79 | } |
80 | |
81 | private double parseNumber(Object src) { |
82 | double tag = 0; |
83 | try { |
84 | tag = Double.parseDouble(src.toString()); |
85 | } catch (Exception e) { |
86 | tag = 0; |
87 | } |
88 | return tag; |
89 | } |
90 | |
91 | private boolean isString(Object src) { |
92 | String kind = src.getClass().getName(); |
93 | if ("java.lang.String".equals(kind)) return true; |
94 | return false; |
95 | } |
96 | |
97 | private boolean isNumber(Object src) { |
98 | if (src == null) return false; |
99 | String[] types = new String[] { "java.lang.Character", "java.lang.Byte", "java.lang.Short", "java.lang.Integer", "java.lang.Long", "java.lang.Float", "java.lang.Double" }; |
100 | String kind = src.getClass().getName(); |
101 | for (int i = 0; i < types.length; i++) { |
102 | if (types[i].equalsIgnoreCase(kind)) return true; |
103 | } |
104 | return false; |
105 | } |
106 | |
107 | private Object calculate(String src) { |
108 | if (data.containsKey(src)) { |
109 | return data.get(src); |
110 | } else { |
111 | return null; |
112 | } |
113 | } |
114 | |
115 | private int lastOperator(String src, String[] operators) { |
116 | int tag = -1; |
117 | for (int i = 0; i < operators.length; i++) { |
118 | int pos = src.lastIndexOf(operators[i]); |
119 | if (pos < 0) continue; |
120 | if (tag < 0) { |
121 | tag = pos; |
122 | } else { |
123 | if (pos > tag) { |
124 | tag = pos; |
125 | } |
126 | } |
127 | } |
128 | return tag; |
129 | } |
130 | |
131 | } |
public static class Formula { private Map<String, Object> data; private String formula; public Formula(Map<String, Object> data, String formula) { this.data = data; this.formula = formula; } public static Object calculate(Map<String, Object> data, String formula) { return new Formula(data, formula).calculate(); } public Object calculate() { int pos = lastOperator(formula, new String[] { "+", "-" }); if (pos < 0) { pos = lastOperator(formula, new String[] { "*", "/" }); if (pos < 0) { return calculate(formula); } else { return calculate(formula.substring(0, pos).trim(), formula.charAt(pos) + "", formula.substring(pos + 1).trim()); } } else { return calculate(formula.substring(0, pos).trim(), formula.charAt(pos) + "", formula.substring(pos + 1).trim()); } } private Object calculate(String leftSide, String operator, String rightSide) { Object valLeft = null; Object valRight = null; int pos = lastOperator(leftSide, new String[] { "+", "-" }); if (pos < 0) { pos = lastOperator(leftSide, new String[] { "*", "/" }); if (pos < 0) { valLeft = calculate(leftSide); } else { valLeft = calculate(leftSide.substring(0, pos).trim(), leftSide.charAt(pos) + "", leftSide.substring(pos + 1).trim()); } } else { valLeft = calculate(leftSide.substring(0, pos).trim(), leftSide.charAt(pos) + "", leftSide.substring(pos + 1).trim()); } pos = lastOperator(rightSide, new String[] { "*", "/" }); if (pos < 0) { valRight = calculate(rightSide); } else { valRight = calculate(rightSide.substring(0, pos).trim(), rightSide.charAt(pos) + "", rightSide.substring(pos + 1).trim()); } return calculate(valLeft, operator, valRight); } private Object calculate(Object leftSide, String operator, Object rightSide) { Object tag = null; if (leftSide == null || rightSide == null) return null; if (isNumber(leftSide) && isNumber(rightSide)) { double valLeft = parseNumber(leftSide); double valRight = parseNumber(rightSide); tag = calculate(valLeft, operator, valRight); } else if (isString(leftSide) || isString(rightSide)) { if ("+".equals(operator)) { tag = leftSide.toString() + rightSide.toString(); } } return tag; } private Object calculate(double leftSide, String operator, double rightSide) { if ("+".equals(operator)) { return leftSide + rightSide; } else if ("-".equals(operator)) { return leftSide - rightSide; } else if ("*".equals(operator)) { return leftSide * rightSide; } else if ("/".equals(operator) && rightSide != 0) { return leftSide / rightSide; } else { return null; } } private double parseNumber(Object src) { double tag = 0; try { tag = Double.parseDouble(src.toString()); } catch (Exception e) { tag = 0; } return tag; } private boolean isString(Object src) { String kind = src.getClass().getName(); if ("java.lang.String".equals(kind)) return true; return false; } private boolean isNumber(Object src) { if (src == null) return false; String[] types = new String[] { "java.lang.Character", "java.lang.Byte", "java.lang.Short", "java.lang.Integer", "java.lang.Long", "java.lang.Float", "java.lang.Double" }; String kind = src.getClass().getName(); for (int i = 0; i < types.length; i++) { if (types[i].equalsIgnoreCase(kind)) return true; } return false; } private Object calculate(String src) { if (data.containsKey(src)) { return data.get(src); } else { return null; } } private int lastOperator(String src, String[] operators) { int tag = -1; for (int i = 0; i < operators.length; i++) { int pos = src.lastIndexOf(operators[i]); if (pos < 0) continue; if (tag < 0) { tag = pos; } else { if (pos > tag) { tag = pos; } } } return tag; } }
No comments:
Post a Comment