package com.yg.stack;/*
@author GeQiLin
@date 2020/2/22 14:14
*/
import jdk.nashorn.internal.ir.ReturnNode;
public class Calculator {
/*
* 1.index遍历表达式,一次取出一个字符存入ch中
* 2.若ch是数字放入numStack中,当operStack为空时,如果ch是操作符则存入operStack中
* 3.如果operStack不为空时,当前ch的优先级小于等于operStack【top】则在numStack中取出两个
* 操作数和operStack中取出一个操作符,当ch的优先级大于operStack【top】
* 则将ch存入operStack中
*
* */
public static void main(String[] args) {
String expersion = "300-5*6-20";
int index = 0;//用于遍历expersion
char ch = ' ';//用于记录字符串expersion第index位置的字符
//两个操作数,和一个操作符oper,一个接受计算结果的res
int num1 = 0;
int num2 = 0;
int oper = 0;
int res = 0;
String keepNum = "";//用于进行多位数运算时将ch进行拼接
ArrayStack2 numStack = new ArrayStack2(10);//存放操作数
ArrayStack2 operStack = new ArrayStack2(10);//存放操作符
//循环取出expersion
while (true) {
ch = expersion.substring(index, index + 1).charAt(0);
//ch是否是操作符
if (operStack.isOper(ch)) {
if (!operStack.isEmpty()) {
if (operStack.getPriority(ch) <= operStack.getPriority(operStack.getStackTop())) {
num1 = numStack.pop();
num2 = numStack.pop();
oper = operStack.pop();
res = numStack.doCalculator(num1, num2, oper);
numStack.push(res);
operStack.push(ch);
} else {
//ch优先级小于等于operStack栈顶的优先级直接入栈
operStack.push(ch);
}
} else {
//operStack为空直接入栈
operStack.push(ch);
}
} else {
/* 是操作数,要判段是不是多为数,也就是字符串expersion的index+1处
是不是任是操作数,如果是字符直接进栈
* */
keepNum += ch;
if (index == expersion.length() - 1) {
numStack.push(Integer.parseInt(keepNum));
} else {
if (operStack.isOper(expersion.substring(index + 1, index + 2).charAt(0))) {
numStack.push(Integer.parseInt(keepNum));
keepNum = "";
}
}
}
index++;
if (index >= expersion.length()) {
break;
}
}
while (true) {
if (operStack.isEmpty()) {
break;
}
num1 = numStack.pop();
num2 = numStack.pop();
oper = operStack.pop();
//如果operStack中连续两个操作符是-或者/要变成对应的+和*
if (!operStack.isEmpty() && oper == operStack.getStackTop() && oper == '-') {
oper = '+';
}
res = numStack.doCalculator(num1, num2, oper);
numStack.push(res);
}
System.out.println(expersion + "=" + numStack.getStackTop());
}
}
class ArrayStack2 {
private int maxSize;//栈的大小
private int[] stack;//用数组模拟栈存放数据
private int top = -1;//栈的标识
public ArrayStack2(int maxSize) {
this.maxSize = maxSize;
stack = new int[maxSize];
}
//判断栈是否为空
public boolean isEmpty() {
return top == -1;
}
//判断栈是否为满
public boolean isFull() {
return top == maxSize - 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 void list() {
if (isEmpty()) {
System.out.println("栈空没有数据");
return;
}
for (int i = top; i >= 0; i--) {
System.out.printf("\t" + stack[i]);
}
}
//判断当前字符是否为操作数
public boolean isOper(char c) {
return c == '+' || c == '-' || c == '*' || c == '/';
}
//查看当前栈顶元素
public int getStackTop() {
if (isEmpty()) {
System.out.println("栈空");
return 0;
}
return stack[top];
}
//执行计算操作
public int doCalculator(int num1, int num2, int oper) {
int value = 0;
switch (oper) {
case '+':
value = num1 + num2;
break;
case '-':
value = num2 - num1;
break;
case '*':
value = num1 * num2;
break;
case '/':
if (num1 == 0) {
throw new RuntimeException("被除数不能为0");
}
value = num2 / num1;
break;
default:
System.out.println("参数有误");
break;
}
return value;
}
//得到操作符的优先级
public int getPriority(int ch) {
if (ch == '+' || ch == '-') {
return 0;
} else if (ch == '*' || ch == '/') {
return 1;
} else {
return 0;
}
}
}
栈实现计算机复杂计算
猜你喜欢
转载自blog.csdn.net/lin1214000999/article/details/104449518
今日推荐
周排行