只针对 ( + - * / )进行计算
一、栈
1、相比较之前设置的栈,增加四个新功能为后面做服务。
(1)比较操作符的优先级;
(2)判断是否是操作符;
(3)查看栈顶元素,只是查看,并非取出;
(4)数字与数字之间的计算。
2、栈实现计算机的基本思想:
(1)设置两个栈,用来存放运算符和数字;
(2)判断是否是操作符,如果是,再判断运算符栈是否为空,如果不为空,查看栈顶元素的操作符优先级,与当前操作符优先级进行比较,如果栈顶操作符优先级较大,就从数字栈弹出两个数,操作符栈弹出栈顶元素,进行计算,将计算的值压入数字栈。
(3)最后如果操作符栈为空,就退出,数字栈所剩的数就是表达式的运算结果。
二、具体实现
1.新增功能
代码如下(示例):
// 返回栈顶值,不是出栈
public int peek(){
return stack[top];
}
// 优先级
public int priority(int opr){
if(opr == '*' || opr == '/'){
return 1;
}else if(opr == '+' || opr == '-'){
return 0;
}else {
return -1;
}
}
// 确定是否是操作符
public boolean isOpr(char opr){
return opr == '*' || opr == '/' || opr == '+' || opr == '-';
}
// 计算
public int cal(int num1,int num2,int opr){
int res = 0;
switch (opr){
case '+':
res = num1 + num2;
break;
case '-':
res = num2 - num1;
break;
case '*':
res = num1 * num2;
break;
case '/':
res = num2 / num1;
break;
}
return res;
}
2.主体
代码如下(示例):
while(true){
//依次得到expression 每一个字符
ch = expression.substring(index,index+1).charAt(0);
if(oprStack.isOpr(ch)){ // 如果是操作符
if(!oprStack.isEmpty()){
//如果不为空就和操作符栈顶符号比较优先级
if(oprStack.priority(ch) <= oprStack.priority(oprStack.peek())){
num1 = numStack.pop();
num2 = numStack.pop();
opr = oprStack.pop();
res = numStack.cal(num1,num2,opr);
// 把计算值和运算符入栈
numStack.push(res);
oprStack.push(ch);
}else{
oprStack.push(ch);
}
}else {
// 如果为空直接入栈
oprStack.push(ch);
}
}else { // 如果是数
//numStack.push(ch - 48);//只能是一位数的运算
str += ch;
// 如果ch是expression是最后一位,就直接入栈
if(index == expression.length() - 1){
numStack.push(Integer.parseInt(str));
}else {
if(oprStack.isOpr(expression.substring(index+1,index+2).charAt(0))){
// 如果后一位是运算符
numStack.push(Integer.parseInt(str));
str = "";
}
}
}
// 让index++
index++;
if(index >= expression.length()){
break;
}
}
// 当表达式扫描完毕
while (true){
if (oprStack.isEmpty()){
break;
}
num1 = numStack.pop();
num2 = numStack.pop();
opr = oprStack.pop();
res = numStack.cal(num1,num2,opr);
numStack.push(res);
}
//输出最终结果
int res2 = numStack.pop();
System.out.printf("表达式:%s = %d",expression,res2);