栈实现综合计算器(Java中缀表达式)
程序员文章站
2022-05-26 12:09:48
...
思路如下:
代码如下
package day04;
public class Calcoluate {
public static void main(String[] args) {
//创建两个栈 数字栈和符号栈
ArrayStack2 numStack = new ArrayStack2(10);
ArrayStack2 operateStack = new ArrayStack2(10);
//定义要计算的表达式
String expression = "79-60*2/5";
//定义索引再遍历表达式
int index = 0;
// num1和num2 表达从数栈中取出的值
int num1 = 0;
int num2 = 0;
//operate 表达从符号栈中取出的值
int operate = 0;
char ch = ' ';
int res = 0; //用来保存最后的结果
String keepNum = ""; //用来拼接多位数的问题
//开始遍历表达式
while (true){
ch = expression.substring(index,index+1).charAt(0);
//判断ch是什么 然后进行相应的操作
//1. 判断ch是否是符号
if(operateStack.isOperate(ch)){
//2.符号进行的操作
//2.1如果符号栈为空 那么就直接入栈
if(operateStack.isEmpty()){
operateStack.push(ch);
}else if(operateStack.proviate(ch)>operateStack.proviate( operateStack.getTop())){ //如果当前符号的运算符优先级 大于栈中符号的优先级 就直接入栈
operateStack.push(ch);
}else{//如果当前符号的运算符优先级 小于等于栈中符号的优先级
//就从数栈中pop两个数 和从符号栈中pop出一个符号进行计算,然后将计算的结果入数栈
num1 = numStack.pop();
num2 = numStack.pop();
operate = operateStack.pop();
//计算结果
int res1 = numStack.res(num1, num2, operate);
//将运算的结果入栈
numStack.push(res1);
//将当前符号入栈
operateStack.push(ch);
}
}else{
//数字进行的操作
// numStack.push(ch-48);
keepNum+=ch;
//如果是最后一位数就直接入栈
if(index == expression.length()-1){
numStack.push(Integer.parseInt(keepNum));
}else{
//如果下一位是符号就入数栈
if(numStack.isOperate(expression.substring(index+1,index+2).charAt(0))){
numStack.push(Integer.parseInt(keepNum));
//将keepNum 重新初始化
keepNum = "";
}
}
}
index ++;
if(index>=expression.length()){
break;
}
}
//表达式扫描完毕, 顺序从数栈和符号栈中的pop出相应的数和符号 运行
while (true){
//当符号栈为空 就结束循环
if(operateStack.isEmpty()){
break;
}
num1 = numStack.pop();
num2 = numStack.pop();
operate = operateStack.pop();
res = numStack.res(num1, num2, operate);
System.out.println(res);
//然后将计算的结果再放入数栈
numStack.push(res);
}
System.out.printf("%s的值为%d\n",expression,numStack.pop());
}
}
class ArrayStack2{
public int maxSize; //栈的大小
public int[] stack; //使用数组来模拟栈
public int top = -1; //表示的是栈顶
public ArrayStack2(int maxSize) {
this.maxSize = maxSize;
stack = new int[maxSize];
}
//获取栈顶的值 但是不弹出栈
public int getTop(){
return stack[top];
}
//判断是栈是否满了
public boolean isFull(){
return top == maxSize-1;
}
//判断栈是否为空
public boolean isEmpty(){
return top==-1;
}
//入栈
public void push(int value){
if (isFull()){
System.out.println("栈满");
return;
}
top++;
stack[top] = value;
}
//出栈
public int pop(){
if(isEmpty()){
throw new RuntimeException("栈里面没有数据了~");
}
int value = stack[top];
top--;
return value;
}
//判断符号的优先级 优先级越大的值越大
public int proviate(int operate){
if(operate == '*' || operate == '/'){
return 1;
}else if(operate== '+' || operate=='-'){
return 0;
}else{
return -1;
}
}
//判断是否是符号
public boolean isOperate(char operate){
return operate == '*' || operate=='/' || operate =='+' || operate=='-';
}
//计算表达式的结果
public int res(int num1,int num2,int ch){
int result = 0;
switch (ch){
case '*':
result = num1* num2;
break;
case '/':
result = num2/num1; //除法和减法需要更换位置,因为栈结构是先进后出
break;
case '+':
result = num1+num2;
break;
case '-':
return num2-num1;
}
return result;
}
//遍历栈
public void showStack(){
if (isEmpty()){
System.out.println("栈空");
return;
}
for (int i = top; i >=0 ; i--) {
System.out.printf("stack[%d]=%d\n",i,stack[i]);
}
}
}