堆栈的应用:四则表达式运算
来源:互联网 发布:微小秘微信营销软件 编辑:程序博客网 时间:2024/09/21 09:29
堆栈的经典应用,四则表达式的元算。这里只能操作的符号是:+ - * / ()。不支持大括号...
下面是代码:
package net.itaem.test;import java.util.ArrayList;import java.util.LinkedList;import java.util.List;import java.util.Stack;/** * 堆栈的应用 * 使用这个堆栈完成四则表达式的运算 四则:+ - * // * 比如:3 + (15-1)*2 -10 = 21 * */public class StackApply {//四则表达式,也就是中缀表达式private String source;//程序不验证输入的表达式是否合法,所以请保证输入的表达式有效,否则计算结果可能无效//要求结果的四则表达式public StackApply(String source){if(source == null || "".equals(source)) throw new RuntimeException("输入的表达式不能为空");this.source = source;}//将中缀表达式变成后缀表达式public List<String> toLaterPattern(){//定义一个堆栈,用来保存操作符号Stack<Character> calStack = new Stack<Character>();//定义一个顺序表,用来存储表达式中的数字List<Integer> intList = new LinkedList<Integer>();//后缀表达式的最后结果List<String> resultList = new ArrayList<String>();//取出中缀表达式里面的全部数字String[] intArrays = source.split("[^0-9]");//将数字添加到集合中,并且去掉空值for(String intArray: intArrays){if(!"".equals(intArray)){intList.add(Integer.parseInt(intArray));}}int index = 0;int fromIndex = 0;//遍历后缀表达式for(int i=0; i<source.length();){//如果是数字,将数字添加到后缀表达式中if(isNumber(source.charAt(i))){//添加数值到结果集resultList.add(intList.get(index) + "");//查看这个数值占用的位数int intLength = (intList.get(index) + "").length();//修改下一个i的值i = source.indexOf(intList.get(index) + "", fromIndex) + intLength;//记录下下一个数值的起始处fromIndex = i;index++;}//如果是 + - * / ( ) 这四个符号,进行进出站操作else if(isCalculator(source.charAt(i))){//如果是'(',进入堆栈if(source.charAt(i) == '('){calStack.add(source.charAt(i));//弹出第一栈顶到第一个(之间的操作符号}else if(')' == source.charAt(i)){ //将数字的内容出栈Character pop = null;//输出()之间的内容while((pop = calStack.pop()) != '('){char[] p = new char[1];p[0] = pop;//将出栈的内容添加到结果集中resultList.add(new String(p));}}else{ //这里处理 + - * /的情况//是* /if(source.charAt(i) == '*' || source.charAt(i) == '/'){calStack.push(source.charAt(i)); //因为 * /的优先级比较高,直接压入堆栈之中}else if(source.charAt(i) == '+' || source.charAt(i) == '-'){//判断堆栈里面的内容,看看优先级关系if(calStack.isEmpty()){ //如果为空,直接添加进去堆栈之中calStack.push(source.charAt(i));}else{//取出第一个运算符号,这里不是弹出char pop = calStack.peek();//查看是否是优先级比较高的符号if(pop == '*' || pop == '/'){while(!calStack.isEmpty()){ //输出所有优先级比较高的运算符pop = calStack.pop();if(pop == '*' || pop == '/'){ //如果是 * /,优先级比较高,压入到堆栈中resultList.add(pop + ""); }else{ //优先级比较低,停止break; }}//弹出完成之后,要将此次的操作符添加到堆栈中calStack.push(source.charAt(i));}else{ //如果是相同优先级的+ -,添加到堆栈之中// 1-2-3-4不满足结合律,所以要特殊处理,将数字改变为负数if(source.charAt(i) == '-' && pop == '-'){resultList.set(index-1, -intList.get(index-1) + "");}calStack.push(source.charAt(i));}}}}i++;}}//将堆栈里面所有的操作符号取出来List<String> pops = new LinkedList<String>();while(!calStack.isEmpty()){pops.add(calStack.pop()+"");}for(String pop: pops){resultList.add(pop);}return resultList;}public String each(char c){return null;}private boolean isCalculator(char c) {switch(c){case '+':case '-':case '*':case '/':case '(':case ')':return true;default:return false;}}//判断一个字符是否是数字private boolean isNumber(char c) {switch(c){case '0':case '1':case '2':case '3':case '4':case '5':case '6':case '7':case '8':case '9':return true;default:return false;}}//返回计算结果public float result(){//得到后缀运算表达式的内容List<String> laterPattern = toLaterPattern();//用来保存计算结果的堆栈Stack<Float> floatStack = new Stack<Float>();float calResult = 0;//计算结果//计算过程:如果是数字,进堆栈,如果是运算操作符,出栈,然后执行运算,再将运算结果压入堆栈for(String c: laterPattern){if(c.matches("-?\\d+")){ //将数字取出来,然后压入堆栈中//将数字压入到堆栈中floatStack.push(Float.parseFloat(c));}else{//取出两个操作数float first = floatStack.pop();float second = 0;//处理是负数的情况if(!floatStack.isEmpty()){second = floatStack.pop();}char choose = c.toCharArray()[0];switch(choose){case '+': calResult = second+first;break;case '-': //2-(-2)==4,所以这里要特殊处理if(first > 0){ calResult = second - first;}else{calResult = second + first;}break;case '*': calResult = second*first;break;case '/': calResult = second/first; //记得转为float,避免出现 3/2 == 1的情况break;default:throw new RuntimeException("操作符有错误...目前暂且不支持+ - * / ( ) 之外的运算符");}//将计算结果压入堆栈floatStack.push(calResult);}}//最后一个栈顶元素就是结果return floatStack.pop();}public static void main(String[] args) {System.out.println("1+2+3+4 = " + new StackApply("1+2+3+4").result());System.out.println("1+2+3*4 = " + new StackApply("1+2+3*4").result());System.out.println("(-11)+2+3*4 = " + new StackApply("(-11)+2+3*4").result());System.out.println("11+2/3*4 = " + new StackApply("11+2/3*4").result());System.out.println("1*2*3*4 = " + new StackApply("1*2*3*4").result());System.out.println("1/(2/(3/4)) = 1/2/3/4 = " + new StackApply("1/2/3/4").result() + " = " + new StackApply("1/2/3/4").result()); //相当于是 1/(2/(3/4))System.out.println("1+2*3-1 = " + new StackApply("1+2*3-1").result());System.out.println("1-2-3-4 = " + new StackApply("1-2-3-4").result());}}
上面的代码可能有点乱,不过主要的思想就是堆栈的应用
运算结果:
1+2+3+4 = 10.01+2+3*4 = 15.0(-11)+2+3*4 = 3.011+2/3*4 = 11.1666671*2*3*4 = 24.01/(2/(3/4)) = 1/2/3/4 = 0.375 = 0.3751+2*3-1 = 5.01-2-3-4 = -8.0
总结:堆栈是一个FIRST IN LAST OUT,典型的FILO的数据结构。在计算机中,应用很广泛,大家可以认真研究下...
0 0
- 堆栈的应用:四则表达式运算
- 后缀表达式+栈的应用=四则表达式运算
- 栈的应用——四则表达式
- 堆栈的应用--计算机对运算表达式编译
- 四则混合运算表达式分析程序的原理及其实现
- 利用堆栈实现四则表达式运算器
- 栈的应用——四则表达式求值
- 栈的应用——四则表达式求值
- 数据结构之栈的应用——四则表达式求值
- 栈的应用——四则表达式求值
- 计算四则混合运算表达式(不用栈)
- c++ 直接中缀表达式求值 仅支持正整数的四则混合运算
- 四则表达式
- 堆栈的应用之计算数学表达式
- 堆栈应用:表达式计算
- 堆栈应用:表达式求值
- 四则混合运算表达式分析程序----C#递归分析版
- 四则混合运算C++代码(中缀表达式)
- 28、线性表
- uiwebview隐藏滚动条,上下滚动时出边界的黑色的背景
- 代码面试最常用的10大算法
- JS产生随机数的几个用法!
- 怎样让WinCE6.0 ARM套件下的USB摄像头工作
- 堆栈的应用:四则表达式运算
- Python语言快速入门
- Tomcat version 6.0 only supports J2EE 1.2, 1.3, 1.4, and Java EE 5
- python实现插入排序算法的顺序和倒序
- VC++下使用ADO编写数据库程序 – 操作大全
- Android使用Andbase快速开发框架实现常见侧滑栏和滑动标签页组合效果
- ios 百度地图 使用详解
- NYOJ33蛇形填数
- BeginInvoke-异步结果模式