java.util.stack 适合带有小括号的算术运算
内容导读
互联网集市收集整理的这篇技术教程文章主要介绍了java.util.stack 适合带有小括号的算术运算,小编现在分享给大家,供广大互联网技能从业者学习和参考。文章包含11552字,纯文字阅读大概需要17分钟。
内容图文
![java.util.stack 适合带有小括号的算术运算](/upload/InfoBanner/zyjiaocheng/601/8fb4509cb6f44cf48f2c93ac89198770.jpg)
java.util.stack,继承自Vector
FILO, 适合带有小括号的算术运算
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 136 137 138 139 140 141 142 143 144 145 146 147 148 149 150 151 |
import java.util.Stack;
/**?
? * 利用栈,进行四则运算的类?
? * 用两个栈来实现算符优先,一个栈用来保存需要计算的数据numStack,一个用来保存计算优先符priStack?
? *?
? * 基本算法实现思路为:用当前取得的运算符与priStack栈顶运算符比较优先级:若高于,则因为会先运算,放入栈顶;?
? * 若等于,因为出现在后面,所以会后计算,所以栈顶元素出栈,取出操作数运算;?
? * 若小于,则同理,取出栈顶元素运算,将结果入操作数栈。各个优先级'(' > '*' = '/' > '+' = '-' > ')'?
? *?
? */
public class Operate {??
?? private Stack<Character> priStack = new Stack<Character>(); // 操作符栈??
?? private Stack<Integer> numStack = new Stack<Integer>();; // 操作数栈??
???
?? /**?
??? * 传入需要解析的字符串,返回计算结果(此处因为时间问题,省略合法性验证)?
??? * @param str 需要进行技术的表达式?
??? * @return 计算结果?
??? */
?? public int caculate(String str) {??
???? // 1.判断string当中有没有非法字符??
???? String temp; // 用来临时存放读取的字符??
???? // 2.循环开始解析字符串,当字符串解析完,且符号栈为空时,则计算完成??
???? StringBuffer tempNum = new StringBuffer(); // 用来临时存放数字字符串(当为多位数时)??
???? StringBuffer string = new StringBuffer().append(str); // 用来保存,提高效率??
???
???? while (string.length() != 0 ) {??
?????? temp = string.substring( 0 , 1 );??
?????? string.delete( 0 , 1 );??
?????? // 判断temp,当temp为操作符时??
?????? if (!isNum(temp)) {??
???????? // 1.此时的tempNum内即为需要操作的数,取出数,压栈,并且清空tempNum??
???????? if (! "" .equals(tempNum.toString())) {??
?????????? // 当表达式的第一个符号为括号??
?????????? int num = Integer.parseInt(tempNum.toString());??
?????????? numStack.push(num);
?????????? tempNum.delete( 0 , tempNum.length());??
???????? }??
???????? // 用当前取得的运算符与栈顶运算符比较优先级:若高于,则因为会先运算,放入栈顶;若等于,因为出现在后面,所以会后计算,所以栈顶元素出栈,取出操作数运算;??
???????? // 若小于,则同理,取出栈顶元素运算,将结果入操作数栈。??
???
???????? // 判断当前运算符与栈顶元素优先级,取出元素,进行计算(因为优先级可能小于栈顶元素,还小于第二个元素等等,需要用循环判断)??
???????? while (!compare(temp.charAt( 0 )) && (!priStack.empty())) {?
?????????? int a = ( int ) numStack.pop(); // 第二个运算数??
?????????? int b = ( int ) numStack.pop(); // 第一个运算数??
?????????? char ope = priStack.pop();??
?????????? int result = 0 ; // 运算结果??
?????????? switch (ope) {??
?????????? // 如果是加号或者减号,则??
?????????? case '+' :??
???????????? result = b + a;??
???????????? // 将操作结果放入操作数栈??
???????????? numStack.push(result);??
???????????? break ;??
?????????? case '-' :??
???????????? result = b - a;??
???????????? // 将操作结果放入操作数栈??
???????????? numStack.push(result);??
???????????? break ;??
?????????? case '*' :??
???????????? result = b * a;??
???????????? // 将操作结果放入操作数栈??
???????????? numStack.push(result);??
???????????? break ;??
?????????? case '/' :??
???????????? result = b / a; // 将操作结果放入操作数栈??
???????????? numStack.push(result);??
???????????? break ;??
?????????? }??
???
???????? }??
???????? // 判断当前运算符与栈顶元素优先级, 如果高,或者低于平,计算完后,将当前操作符号,放入操作符栈??
???????? if (temp.charAt( 0 ) != '#' ) {??
?????????? priStack.push( new Character(temp.charAt( 0 )));??
?????????? if (temp.charAt( 0 ) == ')' ) { // 当栈顶为'(',而当前元素为')'时,则是括号内以算完,去掉括号??
???????????? priStack.pop();??
???????????? priStack.pop();??
?????????? }??
???????? }??
?????? } else
???????? // 当为非操作符时(数字)??
???????? tempNum = tempNum.append(temp); // 将读到的这一位数接到以读出的数后(当不是个位数的时候)??
???? }??
???? return numStack.pop();??
?? }??
???
?? /**?
??? * 判断传入的字符是不是0-9的数字?
??? *?
??? * @param str?
??? *????? 传入的字符串?
??? * @return?
??? */
?? private boolean isNum(String temp) {??
???? return temp.matches( "[0-9]" );??
?? }??
???
?? /**?
??? * 比较当前操作符与栈顶元素操作符优先级,如果比栈顶元素优先级高,则返回true,否则返回false?
??? *?
??? * @param str 需要进行比较的字符?
??? * @return 比较结果 true代表比栈顶元素优先级高,false代表比栈顶元素优先级低?
??? */
?? private boolean compare( char str) {??
???? if (priStack.empty()) {??
?????? // 当为空时,显然 当前优先级最低,返回高??
?????? return true ;??
???? }??
???? char last = ( char ) priStack.lastElement();??
???? // 如果栈顶为'('显然,优先级最低,')'不可能为栈顶。??
???? if (last == '(' ) {??
?????? return true ;??
???? }??
???? switch (str) {??
???? case '#' :??
?????? return false ; // 结束符??
???? case '(' :??
?????? // '('优先级最高,显然返回true??
?????? return true ;??
???? case ')' :??
?????? // ')'优先级最低,??
?????? return false ;??
???? case '*' : {??
?????? // '*/'优先级只比'+-'高??
?????? if (last == '+' || last == '-' )??
???????? return true ;??
?????? else
???????? return false ;??
???? }??
???? case '/' : {??
?????? if (last == '+' || last == '-' )??
???????? return true ;??
?????? else
???????? return false ;??
???? }??
?????? // '+-'为最低,一直返回false??
???? case '+' :??
?????? return false ;??
???? case '-' :??
?????? return false ;??
???? }??
???? return true ;??
?? }??
???
?? public static void main(String args[]) {??
???? Operate operate = new Operate();??
???? int t = operate.caculate( "(3+4*(4*10-10/2)#" );???
???? System.out.println(t);??
?? }??
???
}
|
补充:java stack实现的中缀简单四则运算表达式计算
我就废话不多说了,大家还是直接看代码吧~
1 2 3 4 5 6 7 8 |
public abstract class Stack<T> {
?? public abstract boolean isEmpty();
?? public abstract boolean isFull();
?? public abstract T top();
?? public abstract boolean push(T x);
?? public abstract T pop();
?? public abstract void clear();
}
|
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 |
public class SeqStack<T> extends Stack<T> {
?? private Object[] elementData;
?? private int maxTop;
?? private int top;
?? public SeqStack( int size) {
???? this .maxTop = size - 1 ;
???? elementData = new Object[size];
???? top = - 1 ;
?? }
?? @Override
?? public boolean isEmpty() {
???? return top == - 1 ;
?? }
?? @Override
?? public boolean isFull() {
???? return top == maxTop - 1 ;
?? }
?? @SuppressWarnings ( "unchecked" )
?? @Override
?? public T top() {
???? if (top == - 1 ) {
?????? System.out.println( "Empty" );
?????? return null ;
???? }
???? return (T) elementData[top];
?? }
?? @Override
?? public boolean push(T x) {
???? if (top == maxTop) {
?????? System.err.println( "Full" );
?????? return false ;
???? }
???? elementData[++top] = x;
???? return true ;
?? }
?? @SuppressWarnings ( "unchecked" )
?? @Override
?? public T pop() {
???? if (top == - 1 ) {
?????? System.err.println( "Empty" );
?????? return null ;
???? }
????
???? T result = (T)elementData[top];
???? elementData[top] = null ; //gc
???? top--;
???? return result;
?? }
?? @Override
?? public void clear() {
????
???? //let gc do its work
???? for ( int i = 0 ; i < top+ 1 ; i++) {
??????
?????? elementData[i] = null ;
???? }
????
???? top = - 1 ;
?? }
}
|
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 136 137 138 139 140 141 142 |
public class StackCalc {
?? private SeqStack<Integer> stack;
?? public StackCalc( int maxSize) {
???? stack = new SeqStack<Integer>(maxSize);
?? }
?? private void pushOperand(Integer number) {
???? stack.push(number);
?? }
?? private Number doOperate( char oper) {
???? Integer right = stack.pop();
???? Integer left = stack.pop();
???? Integer result = null ;
???? if (left != null && right != null ) {
?????? switch (oper) {
?????? case '+' :
???????? result = left.intValue() + right.intValue();
???????? break ;
?????? case '-' :
???????? result = left.intValue() - right.intValue();
???????? break ;
?????? case '*' :
???????? result = left.intValue() * right.intValue();
???????? break ;
?????? case '/' :
???????? if (right.intValue() == 0 ) {
?????????? System.err.println( "Divide by 0" );
???????? }
???????? result = left.intValue() / right.intValue();
???????? break ;
?????? default :
???????? break ;
?????? }
???? }
???? stack.push(result);
???? return result;
?? }
?? private int icp( char c) {
???? switch (c) {
???? case '#' :
?????? return 0 ;
???? case '(' :
?????? return 7 ;
???? case '*' :
?????? return 4 ;
???? case '/' :
?????? return 4 ;
???? case '+' :
?????? return 2 ;
???? case '-' :
?????? return 2 ;
???? case ')' :
?????? return 1 ;
???? default :
?????? return - 1 ;
???? }
?? }
?? private int isp( int c) {
???? switch (c) {
???? case '#' :
?????? return 0 ;
???? case '(' :
?????? return 1 ;
???? case '*' :
?????? return 5 ;
???? case '/' :
?????? return 5 ;
???? case '+' :
?????? return 3 ;
???? case '-' :
?????? return 3 ;
???? case ')' :
?????? return 7 ;
???? default :
?????? return - 1 ;
???? }
?? }
?? public String transfer(String expression) {
???? StringBuilder sb = new StringBuilder();
???? SeqStack<Character> stack = new SeqStack<Character>(expression.length());
???? stack.push( '#' );
???? for ( int i = 0 ; i < expression.length(); i++) {
?????? Character c = expression.charAt(i);
?????? if ( '0' <= c && c <= '9' || 'a' <= c && c <= 'z' ||
?????????? 'A' <= c && c <= 'Z' ) { // digit character
???????? sb.append(c);
?????? } else { // 操作符
???????? if (icp(c) > isp(stack.top())) { // 进栈
?????????? stack.push(c);
???????? } else { // 出栈
?????????? if (c == ')' ) {
???????????? char ch = stack.pop();
???????????? while (ch != '(' ) {
?????????????? sb.append(ch);
?????????????? ch = stack.pop();
???????????? }
?????????? } else {
???????????? char ch = stack.pop();
???????????? while (icp(c) <= isp(ch)) {
?????????????? sb.append(ch);
?????????????? ch = stack.pop();
???????????? }
???????????? stack.push(ch);
???????????? stack.push(c);
?????????? }
???????? }
?????? }
???? } // end of for
???? char ch = stack.pop();
???? while (ch != '#' ) {
??????
?????? sb.append(ch);
?????? ch = stack.pop();
???? }
???? stack.clear();???
???? return sb.toString();
?? }
?? public Integer calc(String expression) {
???? expression = transfer(expression);
???? for ( int i = 0 ; i < expression.length(); i++) {
?????? char c = expression.charAt(i);
?????? switch (c) {
?????? case '+' :
?????? case '-' :
?????? case '*' :
?????? case '/' :
???????? doOperate(c);
???????? break ;
?????? default :
???????? pushOperand( new Integer(c + "" ));
???????? break ;
?????? }
???? }
???? return stack.pop();
?? }
?? /**
??? * @param args
??? */
?? public static void main(String[] args) {
???? StackCalc calc = new StackCalc( 10 );
???? System.out.println(calc.calc( "6/(4-2)+3*2" ));
?? }
}
|
以上为个人经验,希望能给大家一个参考,也希望大家多多支持脚本之家。如有错误或未考虑完全的地方,望不吝赐教。
您可能感兴趣的文章:- JVM---jstack分析Java线程CPU占用,线程死锁的解决
- Java中使用StackWalker和Stream API进行堆栈遍历
- Java集合Stack源码详解
- Java StackTraceElement实例代码
- Java线程Dump分析工具jstack解析及使用场景
- 深入分析JAVA Vector和Stack的具体用法
- java中stack(栈)的使用代码实例
- Java反射之Call stack introspection详解
内容总结
以上是互联网集市为您收集整理的java.util.stack 适合带有小括号的算术运算全部内容,希望文章能够帮你解决java.util.stack 适合带有小括号的算术运算所遇到的程序开发问题。 如果觉得互联网集市技术教程内容还不错,欢迎将互联网集市网站推荐给程序员好友。
内容备注
版权声明:本文内容由互联网用户自发贡献,该文观点与技术仅代表作者本人。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如发现本站有涉嫌侵权/违法违规的内容, 请发送邮件至 gblab@vip.qq.com 举报,一经查实,本站将立刻删除。
内容手机端
扫描二维码推送至手机访问。