题解 | #四则运算#
四则运算
https://www.nowcoder.com/practice/9999764a61484d819056f807d2a91f1e
//思路:1.先将所有括号替换为小括号 2.处理所有小括号中的表达式,将计算结果存在一个全局变量map映射中3.最后计算整个不含括号的表达式 import java.util.*; import java.lang.*; // 注意类名必须为 Main, 不要有任何 package xxx 信息 public class Main { LinkedHashMap<Character,Integer> lhm = new LinkedHashMap<>();//用于存放小括号中子表达式的计算结果 public static void main(String[] args) { String s = new Scanner(System.in).nextLine(); s=s.replaceAll("[\\[\\{]","("); s=s.replaceAll("[\\]\\}]",")"); Main me = new Main(); char a='A'; //使用while循环处理子表达式,直至最终的表达式中不含括号 while (s.contains("(")){ int indl = s.lastIndexOf("("); int indr = s.indexOf(")",indl); StringBuilder sb = new StringBuilder(); sb.append(s); String s0 = s.substring(indl+1,indr); int sum0 = me.evalbase(s0); //使用原表达式中不可能出现的字符替换子表达式的计算结果,将其映射的value值存在全局变量lhm中 me.lhm.put(a,sum0); sb.replace(indl,indr+1,Character.toString(a)); s=sb.toString(); a+=1; } //将最后的表达式计算后输出结果 System.out.println(me.evalbase(s)); } //计算不含括号的表达式的方法: int evalbase(String s){ Stack<Integer> st = new Stack<>(); char preop='+';//预置上一个符号为“+” int step=0;//用来存放for循环的步长,数字为对应数字的长度,符号为1 //将数字、加减乘除分别处理,遇见数字则往后取直到取完整个数字串,将取到的数字按照其前边的符号处理后推入栈 for (int i=0;i<s.length();i+=step){ char ci = s.charAt(i); //---处理数字,两种情况:数字串和映射在全局map变量中的值 if (Character.isDigit(ci) || (ci>='A' && ci<='Z')){ int num=0;step=0;//每次取数前将num和步长置0 while (Character.isDigit(ci)){//使用while循环取数字串 step+=1; num = num*10+(ci-'0'); if (i+step>s.length()-1){ break;//若已到最后一位,跳出循环 } ci = s.charAt(i+step); } if (ci>='A' && ci<='Z'){//根据key取出映射在全局变量中的子表达式计算结果(因为只定义到Z,所以只支持不超过26个括号的表达式) step+=1; num=this.lhm.get(ci); } //若数字前边符号为减乘以-1,为*则弹出上一个数字相乘,为/则弹出上一个数字相除,为+的不做处理 switch (preop){ case '-': num =-1*num;break; case '*': num = st.pop()*num;break; case '/': num = st.pop()/num;break; } st.push(num); }else if (ci=='-' || ci=='*' || ci=='/' || ci=='+'){ preop = ci;step=1;//设置符号时将for循环的步长设置为1 } } //将栈中的所有数字相加后输出 int re = st.stream().mapToInt(no->no).sum(); return re; } }