目录

1 问题描述

2 解决方案

 


1 问题描述

问题描述
  输入一个只包含加减乖除和括号的合法表达式,求表达式的值。其中除表示整除。
输入格式
  输入一行,包含一个表达式。
输出格式
  输出这个表达式的值。
样例输入
1-2+3*(4-5)
样例输出
-4
数据规模和约定
  表达式长度不超过100,表达式运算合法且运算过程都在int内进行。
 

2 解决方案

具体代码如下:

package com.liuzhen.systemExe;

import java.util.Scanner;
import java.util.Stack; public class Main{
//计算表达式的值
public void getExpressionValue(String A){
char[] arrayA = A.toCharArray();
Stack<Integer> Value = new Stack<Integer>(); //存放运算数字及表达式计算结果
Stack<Character> Operator = new Stack<Character>(); //存放运算符
for(int i = 0;i < A.length();i++){
int temp = 0;
if(arrayA[i] >= '0' && arrayA[i] <= '9'){
temp = arrayA[i] - '0';
i = i + 1;
while(i < A.length() && arrayA[i] >= '0' && arrayA[i] <= '9'){
temp = temp * 10 + (arrayA[i] - '0');
i++;
}
i--; //对应上面一句i = i+1;因为在for循环中有i++自增操作,若不执行此句,会导致i自增两次
Value.push(temp);
}
else{
if(Operator.empty()){
Operator.push(arrayA[i]);
}
else{
char temp1 = Operator.pop(); //进栈前,存放运算符栈中栈顶存放字符
int judge = comparePriority(temp1,arrayA[i]); //比较当前字符与栈顶字符优先级
if(judge == 1){ //当前字符优先级小于栈顶字符
int tempA = Value.pop();
int tempB = Value.pop();
int result = computeNumber(tempB,tempA,temp1);
Value.push(result);
Operator.push(arrayA[i]);
}
if(judge == 0){ //当前字符优先级大于栈顶字符
Operator.push(temp1);
Operator.push(arrayA[i]);
}
if(judge == 2){ //字符')'遇到'(',刚好使得'('出栈
System.out.println("'('刚好遇到')'"); //这种情况也应该不会出现,按照给定优先级,')'一般会先遇到+、-、*、/字符
}
if(judge == 3){ //此时')'刚好准备进栈
while(temp1 != '('){ //')'字符要等到第一个'('出栈才能结束循环
//System.out.println(temp1);
int tempA = Value.pop();
int tempB = Value.pop();
int result = computeNumber(tempB,tempA,temp1);
Value.push(result);
temp1 = Operator.pop();
}
}
if(judge == -1){ //此时,说明当前栈顶字符为')',这是不存在的,因为遇到')',按要求不让进栈
System.out.println("出现栈顶有')'错误!!!");
}
}
}
} while(!Operator.empty() && !Value.empty()){ //此时,字符栈中还存在运算符的情况
char temp1 = Operator.pop();
int tempA = Value.pop();
int tempB = Value.pop();
int result = computeNumber(tempB,tempA,temp1);
Value.push(result);
}
System.out.println(Value.pop()); //此时运算符栈为空,数字栈中只存在表达式计算最终结果
}
//计算a operator b的值,operator = {+,-,*,/}
public int computeNumber(int a,int b,char operator){
int result;
switch(operator){
case '+':
result = a+b;
break;
case '-':
result = a-b;
break;
case '*':
result = a*b;
break;
case '/':
result = a/b;
break;
default:
result = 0;
break;
}
return result;
}
//判断运算符a和b的优先级
public int comparePriority(char a,char b){
//使用二维数组表达运算符之间的优先级,行用字符a表示,列用字符b表示
int[][] Value = {{1,1,0,0,0,3},
{1,1,0,0,0,3},
{1,1,1,1,0,3},
{1,1,1,1,0,3},
{0,0,0,0,0,2},
{-1,-1,-1,-1,-1,-1}};
int i = 0;
int j = 0;
if(a == '+')
i = 0;
if(a == '-')
i = 1;
if(a == '*')
i = 2;
if(a == '/')
i = 3;
if(a == '(')
i = 4;
if(a == ')')
i = 5; if(b == '+')
j = 0;
if(b == '-')
j = 1;
if(b == '*')
j = 2;
if(b == '/')
j = 3;
if(b == '(')
j = 4;
if(b == ')')
j = 5;
return Value[i][j];
} public static void main(String[] args){
Main test = new Main();
Scanner in = new Scanner(System.in);
System.out.println("请输入一个算法表达式:");
String A = in.nextLine();
test.getExpressionValue(A); }
}

运行结果:

请输入一个算法表达式:
1-2+3*(4-5)
-4 请输入一个算法表达式:
1-2*((2+3)*2-(2+3))
-9 请输入一个算法表达式:
1-2*((2+3)*(2+3))
-49

算法笔记_044:表达式计算求值(Java)的更多相关文章

  1. Java实现表达式计算求值

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

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

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

  3. 算法笔记(c++)--求一个数的所有质数因子

    算法笔记(c++)--求一个数的所有质数因子 先贴题目: 这题不难,恶心在理解上面.最后看评论知道了怎么回事: 2*2*3*3*5=180 按照这逻辑的话应该输入的数由一系列质数相乘出来,所以每次找到 ...

  4. C语言对表达式的求值顺序不是明确规定的

    讨论区看到的 WA来自那些递归下降求解的代码. 第一种情况,使用|| 和 &&: 例如s为所给串 int getval() { switch(s[c_s++]) { case 'p': ...

  5. 蓝桥杯 算法训练 ALGO-156 表达式计算

    算法训练 表达式计算   时间限制:1.0s   内存限制:256.0MB 问题描述 输入一个只包含加减乖除和括号的合法表达式,求表达式的值.其中除表示整除. 输入格式 输入一行,包含一个表达式. 输 ...

  6. C++ 中缀转后缀表达式并求值

    //中缀转后缀 #include<iostream> #include<stack> using namespace std; int prio(char x){ ; ; ; ...

  7. 中缀表达式转逆波兰式(后缀表达式)求值 C++ Stack

    给一个包含小数的中缀表达式 求出它的值 首先转换为后缀表达式然后利用stack求出值 转换规则: 如果字符为'('  push else if 字符为 ')' 出栈运算符直到遇到‘(' else if ...

  8. Dijkstra的双栈算术表达式的求值算法

    例如需要计算 ( 1 + (  ( 2 + 3 ) * ( 4 * 5 ) ) ) 我们以字符串的形式输入该表达式,利用两个栈来完成这个操作,其中一个栈保存运算符,一个栈保存操作数,过程是这样的: 表 ...

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

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

随机推荐

  1. luogu P1965 转圈游戏

    题目描述 n 个小伙伴(编号从 0 到 n-1)围坐一圈玩游戏.按照顺时针方向给 n 个位置编号,从0 到 n-1.最初,第 0 号小伙伴在第 0 号位置,第 1 号小伙伴在第 1 号位置,……,依此 ...

  2. [BZOJ1799][AHOI2009]同类分布(数位DP)

    1799: [Ahoi2009]self 同类分布 Time Limit: 50 Sec  Memory Limit: 64 MBSubmit: 1635  Solved: 728[Submit][S ...

  3. nginx部署ssl证书

    确保nginx有ssl模块,修改nginx.conf文件 在server中添加 listen 443 ssl; #crt文件路径 证书的公钥 ssl_certificate xxx.crt; #key ...

  4. 【转】如何修改maven工程jdk版本

    1.使用maven的时候,默认会使用1.5版本的JDK,并且也是编译成1.5的,我的电脑里面用的JDK是1.7的,1.8也出来了,没理由还用1.5的吧!所以我手动改成了1.7,郁闷的是,每次 mave ...

  5. 让Firefox支持offsetX、offsetY

    //计算光标相对于第一个定位的父元素的坐标 function coordinate(e){ var o = window.event || e, coord, coord_X, coord_Y; co ...

  6. mysql表前缀

    之前一直没明白,mysql有些规范里面,建议建表的时候添加前缀,它的意义究竟是为何.直到最近,我想学习一下Swift的网络请求,于是打算在新浪云新建个项目却发现新浪云免费用户最多只能建立5个项目.于是 ...

  7. 断点续传队列和本地持久化(iOS源码)

    // // ASIFormDataRequest.m // Part of ASIHTTPRequest -> http://allseeing-i.com/ASIHTTPRequest // ...

  8. Use two picogate devices for bidirectional level-shifting

    In new mixed-voltage systems, it is often necessary to level-shift a control signal from a high leve ...

  9. SEAndroid安全机制简要介绍和学习计划

    与iOS相比.Android最被人诟病的是其流畅性和安全性. 然而,从4.0開始,Android不遗余力地改善其流畅性. 特别是在即将公布的L版本号中,用ART替换了Dalvik,相信会越来越流畅.至 ...

  10. 内核镜像zImage是如何生成的

    转载:内核镜像zImage是如何生成的 内核镜像zImage是如何生成的 前面两篇文章介绍了vmlinux 文件生成,这个文件必然是核心的linux内核,但是它是ELF格式的文件,其中包含了可执行的二 ...