首先主类Calculate实现的功能比较简单,简单的控制台输入和调用真正的计算方法
public class Calculate {
public static void main(String[] args) {
//控制台输入计算表达式
Scanner scanner = new Scanner(System.in);
String str = scanner.nextLine();
//计算
int result = Operation.calculate(str);
System.out.println(result);
}
}
接下来是实现主要计算功能的类
import java.util.*;
public class Operation {
//创建两个栈分别存放数字和运算符,存放数字的栈由于要做数字拼接所以使用string类型
public static Stack<String> nums = new Stack<>();
public static Stack<String> ops = new Stack<>();
//计算结果
public static int result = 0;
//创建两个栈用来存放乘除算法过后的剩余的加减法运算符和数字
public static Stack<Integer> afterNums = new Stack<>();
public static Stack<String> afterops = new Stack<>();
/**
*计算方法
* @param str
* @return
*/
public static int calculate(String str) {
//分割输入的算法表达式,并存入集合中
String[] strs = str.split("");
List<String> strList = Arrays.asList(strs);
//将计算结果初始化为0
int result = 0;
//解析运算式,分离数字和操作符
putStack(strList);
//计算表达式中的乘法
int temp_result = calculate();
//计算表达式中的加减法
while (!afterops.isEmpty()){
String op = afterops.pop();
switch (op){
case "+":
temp_result = temp_result + afterNums.pop();
break;
case "-":
temp_result = temp_result - afterNums.pop();
break;
}
}
result = temp_result;
return result;
}
/**
* 优先计算表达式中的乘法
* @return
*/
private static int calculate(){
//用于存放计算中的临时数据
String temp;
while (!ops.isEmpty()){
String op = ops.pop();
switch (op){
case "*":
//计算并将计算结果赋值给temp重新压入栈中
result = Integer.parseInt(nums.pop()) * Integer.parseInt(nums.pop());
temp = String.valueOf(result);
nums.push(temp);
break;
case "/":
//这里要注意除数和被除数的位置,所以需要先取出除数和被除数
String divider = nums.pop();
String dividend = nums.pop();
result = Integer.parseInt(dividend) / Integer.parseInt(divider);
temp = String.valueOf(result);
nums.push(temp);
break;
case "+":
case "-":
//将加减法符号存入新符号栈中,并将操作符后面一个数放入新数字栈
afterNums.push(Integer.parseInt(nums.pop()));
afterops.push(op);
break;
}
}
// 返回栈中剩余的最后一个结果
return Integer.parseInt(nums.pop());
}
/**
* 将数字与运算符分割开来并放入各自的栈中
* @param strList
*/
private static void putStack(List<String> strList) {
//定义一个boolean变量用来判断上一个存入栈中的元素是否是数字,是数字的话则会拼接当前的数字
boolean flag = false;
demo:for (int i = 0; i < strList.size(); i++) {
//取当前运算式的第一个字符
String s = strList.get(i);
//判断字符是否是数字
if (Character.isDigit(s.charAt(0))) {
if (flag){
s = nums.pop() + s;
}
//为数字将其放入数字栈中
nums.push(s);
flag=true;
}else {
//字符为运算符,放入操作符栈中
switch (s) {
case "+":
case "-":
case "*":
case "/":
ops.push(s);
flag=false;
break;
default:
//表达式不正确中断整个操作
System.out.println("输入的表达式不正确");
flag=false;
break demo;
}
}
}
}
}
运行结果: