中缀表达式: 中缀表达式就是我们平常生活中使用的表达式,例如:1+3*2,2-(1+3)等等,中缀表达式的特点是:二元运算符总 是置于两个操作数中间。
逆波兰表达式(后缀表达式): 逆波兰表达式是波兰逻辑学家J・卢卡西维兹(J・ Lukasewicz)于1929年首先提出的一种表达式的表示方法,后缀表 达式的特点:运算符总是放在跟它相关的操作数之后。
-- 转换思想:
1、创建一个栈用于保存运算符。
2、从左往右遍历字符串。
3、如果是数字直接输出。
4、如果是运算符:
4.1、如果栈为空直接入栈。
4.2、如果是左括号直接入栈。
4.3、如果是右括号,输出并弹出左括号之上的所有运算符,最后弹出左括号不输出。
4.4、如果是其他运算符,判断栈不为空并且优先级大于等于当前运算符的出栈,最后将运算符入栈。
5、循环结束如果栈还有元素,则将栈中元素弹出并输出。
-- 转换前的中缀表达式:1+23+(45+6)7 -- 转换后的后缀表达式:123+456+7+
-- 代码:
public class Test {
public static void main(String[] args) {
// 中缀表达式
String str = "1+2*3+(4*5+6)*7";
// 调用函数
Trans(str);
}
// 返回当前运算符的优先级
public static int priority(String op) {
int num = 0;
if (op.equals("*") || op.equals("/")) {
// 乘除优先级
return num = 2;
} else if (op.equals("+") || op.equals("-")) {
// 加减优先级
return num = 1;
} else if (op.equals("(")) {
// 左括号优先级
return num = 0;
}
// 返回优先级
return num;
}
// 判断是否是数字
public static boolean isNumber(String str) {
// 利用正则表达式判断是否是数字
Pattern pattern = Pattern.compile("[0-9]*");
return pattern.matcher(str).matches();
}
// 将中缀表达式转换为后缀表达式式
public static void Trans(String str) {
// 创建一个栈用于保存运算符
Stack<String> chars = new Stack<>();
// 从左往右遍历字符串
for (int i = 0; i < str.length(); i++) {
// 将当前字符转换为字符串
String currChar = str.charAt(i) + "";
if (isNumber(currChar)) {
// 如果是数字直接输出
System.out.print(currChar);
} else {
// 如果是运算符
if (chars.isEmpty()) {
// 如果栈为空,直接入栈
chars.push(currChar);
} else if (currChar.equals("(")) {
// 如果是左括号直接入栈
chars.push("(");
} else if (currChar.equals(")")) { // 如果是右括号
while (!chars.top().equals("(")) { // 如果不是左括号直接输出
if (!chars.isEmpty()) {
// 栈不为空,弹出
System.out.print(chars.pop());
}
}
// 将左括号弹出,不输出
chars.pop();
} else { // 如果是其他运算符
// 如果栈不为空,并且栈顶优先级大于等于当前运算则让栈顶运算符出栈
while (!chars.isEmpty() && priority(currChar) <= priority(chars.top())) {
System.out.print(chars.pop());
}
// 当前运算符入栈
chars.push(currChar);
}
}
}
// 循环结束,如果栈中还有元素,将将它们全部弹出
while (!chars.isEmpty()) {
System.out.print(chars.pop());
}
}
}
-- 运行效果图:
@ 以上内容属于个人笔记