/*将中缀表达式--转化为后缀表达式--属于栈的一种应用
*具体思路:
*1.扫描字符串,遇到操作数字符直接不管,存到一个字符串里边
*2.操作符优先级比较--定义了方法
* 栈中优先级高:出栈存进字符串,当前的操作符进栈
* 当前操作符优先级高,直接进栈
* 对于左边括号直接进栈,右边括号涉及栈中出栈
*3.扫描完了在将栈中的出栈和操作数存储在一起
*转化完直观的表现:操作数相对位置不变,操作符相对位置相反
* */
public class IntoSuffixExpression {
private CharStack stack;
private String input;
private String output = ""; public IntoSuffixExpression(String in) {
input = in;
stack = new CharStack(input.length());
} //转化为后缀表达式
public String doTrans(){
for(int i = 0; i < input.length();i++){
char ch = input.charAt(i);
stack.displayStack("For " + ch + " ");
/*分析读到的元素的类型--操作符/操作数(默认添加到输出字符串中)
*对于操作符分类并进行优先级比较 乘除优先级高于加减*/
switch(ch){
case '+':
case '-':
gotOper(ch,1);//需要判断优先级prec1:设定的是当前的优先级
break;
case '*':
case '/':
gotOper(ch,2);//需要判断优先级
break;
case '(':
stack.push(ch);//左括号优先级最高直接进栈
break;
case ')':
gotParent(ch);//碰到右边括号涉及出栈
break;
default:
output = output + ch;//是操作数就直接存在输出字符串中
break;
}
}
//打印战中的操作符返回后缀表达式字符串
while(!stack.isEmpty()){
stack.displayStack("while");
output = output + stack.pop();
}
stack.displayStack("end");
return output;
} //比较当前的操作符与栈里面的操作符优先级--进行不同的操作
public void gotOper(char opThis, int prec1) {
while(!stack.isEmpty()){
char opTop = stack.pop();
if(opTop == '('){ //如果栈中顶是左边括号就进去跳出循环
stack.push(opTop);
break;
}
else{
int prec2;
//记录栈中操作符优先级--加减优先级是1乘除优先级是2
if(opTop == '+' || opTop == '-'){
prec2 = 1;
}
else{
prec2 = 2;
}
//栈中优先级小结束比较--当前执行进栈操作
if(prec2 < prec1){
stack.push(opTop);
break;
}
//栈中优先级大就出栈存储在字符串中
else{
output = output + opTop;
}
}
}
//栈为空就直接进栈或者遇到左边括号也是直接进栈或者栈存储比栈中优先级小的
stack.push(opThis);
} //越到右边括号进行出栈的操作--直到遇到左边括号
public void gotParent(char ch){
while(!stack.isEmpty()){
char chx = stack.pop();
if(chx == '('){
break;
}
else{
output = output + chx;
}
}
} }
 /*计算后缀表达式的值--也用的是栈
* */
public class CalculateSuffixExpression {
private MyStack stack;
private String input; //注意这里传入的字符串是后缀的表达式
public CalculateSuffixExpression(String in) {
input = in;
} //数字进栈,操作符栈中元素出栈对应相应的操作
public long calculateValue(){
stack = new MyStack(20);
char ch;
int j;
long num1,num2,interAns;
for(j = 0;j < input.length();j++){
ch = input.charAt(j);
stack.displayStack("" + ch + "");
if(ch >= '0' && ch <= '9'){ //操作数
stack.push((long)(ch - '0'));
}
else{
num2 = stack.pop();
num1 = stack.pop();
switch(ch){
case'+':
interAns = num1 + num2;
break;
case'-':
interAns = num1 - num2;
break;
case'*':
interAns = num1 * num2;
break;
case'/':
interAns = num1 / num2;
break;
default:
interAns = 0;
}
stack.push(interAns);
}//end else
}//end for
interAns = stack.pop();
return interAns;
}//end method public static void main(String[] args){
//转化后缀表达式
String s = "3+(6*9)+2-6/(3-1)";
IntoSuffixExpression is = new IntoSuffixExpression(s);
String out = is.doTrans(); //计算后缀表达式
CalculateSuffixExpression cse = new CalculateSuffixExpression(out);
long result = cse.calculateValue();
System.out.println(result); } }

表达式求值--Java实现的更多相关文章

  1. 利用栈实现算术表达式求值(Java语言描述)

    利用栈实现算术表达式求值(Java语言描述) 算术表达式求值是栈的典型应用,自己写栈,实现Java栈算术表达式求值,涉及栈,编译原理方面的知识.声明:部分代码参考自茫茫大海的专栏. 链栈的实现: pa ...

  2. 逆波兰表达式求值 java实现代码

    根据逆波兰表示法,求表达式的值. 有效的运算符包括 +, -, *, / .每个运算对象可以是整数,也可以是另一个逆波兰表达式. 说明: 整数除法只保留整数部分. 给定逆波兰表达式总是有效的.换句话说 ...

  3. 表达式求值(java)

    今天去面试,考了这个,短时间没想出来... 太笨了! 后来想用栈和递归做 但是看了网上才知道,可以将中缀表达式转为后缀表达式,就极其方便了. import java.util.Scanner; imp ...

  4. 去空格的四则运算表达式求值-Java

    笔记 package com.daidai.day4.demo1; import java.util.ArrayList; import java.util.Arrays; import java.u ...

  5. leetcode算法学习----逆波兰表达式求值(后缀表达式)

    下面题目是LeetCode算法:逆波兰表达式求值(java实现) 逆波兰表达式即后缀表达式. 题目:  有效的运算符包括 +, -, *, / .每个运算对象可以是整数,也可以是另一个逆波兰表达式.同 ...

  6. java实现算术表达式求值

    需要根据配置的表达式(例如:5+12*(3+5)/7.0)计算出相应的结果,因此使用java中的栈利用后缀表达式的方式实现该工具类. 后缀表达式就是将操作符放在操作数的后面展示的方式,例如:3+2 后 ...

  7. 奇怪的表达式求值 (java实现)

    题目参考:http://blog.csdn.net/fuxuemingzhu/article/details/68484749 问题描述; 题目描述: 常规的表达式求值,我们都会根据计算的优先级来计算 ...

  8. 蓝桥杯算法训练 java算法 表达式求值

    问题描述 输入一个只包含加减乖除和括号的合法表达式,求表达式的值.其中除表示整除. 输入格式 输入一行,包含一个表达式. 输出格式 输出这个表达式的值. 样例输入 1-2+3*(4-5) 样例输出 - ...

  9. Java描述表达式求值的两种解法:双栈结构和二叉树

    Java描述表达式求值的两种解法:双栈结构和二叉树 原题大意:表达式求值 求一个非负整数四则混合运算且含嵌套括号表达式的值.如: # 输入: 1+2*(6/2)-4 # 输出: 3.0 数据保证: 保 ...

随机推荐

  1. es6中对象的类与继承方法

    对于对象,我一直搞不清楚到底是该如何去继承,如何去书写.在熟练es6之后,终于会尝试写出来了. 代码如下: //我们假定父类为person,子类为man class person{ construct ...

  2. OJ题

    题目:在字符串中找出连续最长的数字串 #include <stdlib.h> #include <string.h> #include <iostream> #in ...

  3. Python: 列表注意细节与元组的基本用法

    列表注意细节: 1.list.clear():将列表中成员清空(与del list区别开) 2.list.copy():复制一份相同的列表(浅COPY,只复制列表第一层) 3.如果两个列表相等,如li ...

  4. webpack2系列step1

    第一篇:HTML 本文将一步一步的介绍webpack2的配置,从最基础的一直到与node结合. 操作都一样: midir step1 && cd step1 npm init -y n ...

  5. 多线程简单实例(1)真的需要synchronized么?

    说道多线程的安全问题,很多人想到就就是加锁.用到synchronized关键字. 那就要先说说synchronized问什么能够保证线程安全了. 首先要了解线程的工作方式:线程工作分为工作内存和主内存 ...

  6. Invoke 用法

    转自:http://blog.sina.com.cn/s/blog_5a6f39cf0100s23x.html 在多线程编程中,我们经常要在工作线程中去更新界面显示,而在多线程中直接调用界面控件的方法 ...

  7. 新建maven项目遇到Select an Archetype时没有maven-archetype-webapp处理方法

    [已经有很多博客写过相关的了.详细请去看其他博主的.这里只是记录新建的时候发生的问题给新手提供帮助.因为我跟我的同事都遇到了.因为没记录下来,又花了时间找问题.而网上好像也不多.所以记录下来.希望帮到 ...

  8. Hive任务优化(2)

    JOIN优化 1.大多数情况下,Hive会对每对Join连接对象启动一个MapReduce任务. 2.多表关联时,如果每个ON子句都使用相同的连接键的话,那么只会产生一个MapReduce Job. ...

  9. Mybatis #{ } 和 ${ } 区别

    动态 SQL 是 Mybatis 的强大特性之一,也是它优于其他 ORM 框架的一个重要原因.Mybatis 在对 sql 语句进行预编译之前,会对 sql 进行动态解析,解析为一个 BoundSql ...

  10. 简单Elixir游戏服设计-玩法simple_poker

    上回介绍了玩法,现在编写了玩法的简单建模. 做到现在感觉目前还没有使用umbrella的必要(也许以后会发现必要吧),model 应用完全可以合并到game_server. 代码还在https://g ...