其他分享
首页 > 其他分享> > 栈(应用综合计算器)

栈(应用综合计算器)

作者:互联网

数栈numStack:存放数  符号栈operStack:存放运算符

思路:

  1、通过一个index值 (相当于索引),遍历表达式

  2、如果发现index扫描到是一个数字,直接入数栈

  3、如果扫描到时一个符号,分如下情况:

    1)如果当前符号栈为空,就直接入栈

    2)如果符号栈有操作符,就进行比较,

    如果当前操作符优先级小于等于栈中的操作符

    需要从数栈中pop出两个数,再从符号栈中pop出一个符号,进行运算,将得到的结果再入数栈,然后将当前操作符入符号栈。

    如果当前操作符优先级大于栈中的操作符,就直接入符号栈

  4、当表达式臊面完毕,顺序从数栈和符号栈中pop出相应的数和符号并运算

  5、最后数栈只有一个数字,就是表达式的结果

  1 import com.sun.org.apache.xpath.internal.objects.XBoolean;
  2 
  3 public class Calculator {
  4     public static void main(String[] args) {
  5         //
  6         String expression = "3+2*6-1";
  7         //创建两个栈,数栈,一个符号栈
  8         ArrayStack2 numStack = new ArrayStack2(10);
  9         ArrayStack2 operStack = new ArrayStack2(10);
 10         //定义需要的相关变量
 11         int index = 0;//用于扫描
 12         int num1=0;
 13         int num2=0;
 14         int oper = 0;
 15         int res = 0;
 16         char ch = ' ';//将每次扫描到的char存到ch
 17         //开始while循环的扫描expression
 18         while(true){
 19             //依次得到expression的每一个字符
 20             ch = expression.substring(index,index+1).charAt(0);
 21             //判断ch是什么,然后做相应的处理
 22             if (operStack.isOper(ch)){//如果是运算符
 23                 //判断当前的符号栈是否为空
 24                 if (!operStack.isEmpty()){
 25                     //处理
 26                     if (operStack.priority(ch) <= operStack.priority(operStack.pick())){
 27                         num1 = numStack.pop();
 28                         num2 = numStack.pop();
 29                         oper = operStack.pop();
 30                         res = numStack.cal(num1,num2,oper);
 31                         //把运算的结果入数栈
 32                         numStack.push(res);
 33                         //让后将当前的操作符入符号栈
 34                         operStack.push(ch);
 35                     }else {
 36                         operStack.push(ch);
 37                     }
 38                 }else{
 39                     //如果为空直接入栈
 40                     operStack.push(ch);//1+3
 41 
 42                 }
 43             }else{
 44                 //如果是数,直接入数栈
 45                 numStack.push(ch-48);//字符1 不等于1,ASCII码表
 46 
 47                 //1.当处理多位数,不能发现是一个数就入栈,可能多位数
 48                 //2,在处理数,需要像expression的表达式index后再看一位,如果是数,继续扫描
 49                 //3.因此需要定义一个变量字符串,用于拼接
 50             }
 51             //让index+1,并判断是否扫描到expression最后
 52             index++;
 53             if (index >= expression.length()){
 54                 break;
 55             }
 56         }
 57 
 58         //
 59         while(true){
 60             //如果符号栈为空,则计算到最后结果,数栈只有一个数值【结果】
 61             if (operStack.isEmpty()){
 62                 break;
 63             }
 64             num1 = numStack.pop();
 65             num2 = numStack.pop();
 66             oper = operStack.pop();
 67             res = numStack.cal(num1,num2,oper);
 68             //把运算的结果入数栈
 69             numStack.push(res);
 70         }
 71         int res2 = numStack.pop();
 72         System.out.printf("表达式%s=%d",expression,res2);
 73 
 74 
 75     }
 76 
 77 
 78 }
 79 
 80 //定义一个ArrayStack表示栈,需要扩展功能
 81 class ArrayStack2 {
 82     private int maxSize; //栈的大小
 83     private int[] stack; //数组,数组模拟栈,数据放在该数组
 84     private int top = -1;//top表示栈顶,初始化为-1
 85 
 86     //构造器
 87     public ArrayStack2(int maxSize) {
 88         this.maxSize = maxSize;
 89         stack = new int[this.maxSize];
 90     }
 91     //增加一个方法, 返回当前栈顶的值,不是真正的pop
 92     public int pick(){
 93         return stack[top];
 94     }
 95 
 96     //栈满
 97     public boolean isFull() {
 98         return top == maxSize - 1;
 99     }
100 
101     //栈空
102     public boolean isEmpty() {
103         return top == -1;
104     }
105 
106     //入栈-push
107     public void push(int value) {
108         //先判断栈满
109         if (isFull()) {
110             System.out.println("栈满");
111             return;
112         }
113         top++;
114         stack[top] = value;
115     }
116 
117     //出栈-pop 将栈顶的数据返回
118     public int pop() {
119         //先判断栈是否空
120         if (isEmpty()) {
121             //抛出异常
122             throw new RuntimeException("栈空,没有数据");
123         }
124         int value = stack[top];
125         top--;
126         return value;
127     }
128 
129     //显示栈的情况,遍历时,需要从栈顶开始显示数据
130     public void list() {
131         if (isEmpty()) {
132             System.out.println("栈空,没有数据");
133             return;
134         }
135         //从栈顶显示数据
136         for (int i = top; i >= 0; i--) {
137             System.out.printf("stack[%d]=%d\n", i, stack[i]);
138         }
139     }
140 
141     //扩展:返回运算符的优先级,优先级是自己确定,优先级使用数字表示,数字越大,优先级越高
142     public int priority(int oper){
143         if (oper == '*' || oper == '/'){
144             return 1;
145         }else if (oper == '+' || oper == '-'){
146             return 0;
147         }else {
148             return -1;//假定计算式只含有+ — * /
149         }
150 
151     }
152     //判断是不是一个运算符
153     public boolean isOper(char val){
154         return val == '+' || val == '-' || val == '*' || val == '/';
155     }
156     //计算方法
157     public int cal(int num1,int num2,int oper){
158         int res = 0;//res用于存放计算的结果
159         switch (oper){
160             case'+':
161                 res = num1 + num2;
162                 break;
163             case'-':
164                 res = num2 - num1;//注意顺序
165                 break;
166             case'*':
167                 res = num1 * num2;//注意顺序
168                 break;
169             case'/':
170                 res = num2 / num1;//注意顺序
171                 break;
172             default:
173                 break;
174         }
175         return res;
176     }
177 }

 

    

标签:oper,return,int,top,pop,应用,计算器,public,综合
来源: https://www.cnblogs.com/doremi429/p/16088021.html