一、题目
提取字符串中的最长合法简单数学表达式字符串长度最长的,并计算表达式的值。如果没有返回 0
简单数学表达式只能包含以下内容
0-9 数字,符号+-*
说明:
1.所有数字,计算结果都不超过 long
2.如果有多个长度一样的,请返回第一个表达式的结果
3.数学表达式,必须是最长的,合法的
4.操作符不能连续出现,如 +--+1 是不合法的
二、输入
字符串
三、输出
最长表达式值
四、示例
输入:
1-2abcd
输出:
-1
五、题解
- 理解题意后需要解决 2 个问题:
- 对于求“最长合法表达式”可以使用正则表达式匹配所有合法表达式。注意正则表达式需要使用
?:非捕获组方式,否则匹配不到开始的操作数
- 对于计算表达式值,python 中直接使用
eval函数;java 中需要自己实现,主要思想是操作数栈+操作符栈+运算符优先级,大学数据结构栈的经典应用题目
5.1 Java 实现
package org.stone.study.algo.ex202411;
import java.util.Scanner;
import java.util.Stack;
import java.util.regex.Matcher;
import java.util.regex.Pattern;
public class MaxExprValue {
public static void main(String[] args) {
Scanner scanner = new Scanner(System.in);
String str = scanner.nextLine();
long ans = maxExprValue(str);
System.out.println(ans);
}
public static long maxExprValue(String str) {
int ans = 0;
String regex = "\d+(?:[-+*]\d+)*";
Pattern pattern = Pattern.compile(regex);
Matcher matcher = pattern.matcher(str);
String longestExpr = "";
int maxLen = 0;
while (matcher.find()) {
String expr = matcher.group();
if(expr.length() > maxLen) {
longestExpr = expr;
maxLen = expr.length();
}
}
if(longestExpr.isEmpty()) {
return 0;
}
try {
return evaluateExpr(longestExpr);
} catch (Exception e) {
return 0;
}
}
private static long evaluateExpr(String expr) {
Stack<Long> numStack = new Stack<>();
Stack<Character> opStack = new Stack<>();
int n = expr.length();
long num = 0;
boolean hasNum = false;
for(int i = 0; i < n; i++) {
char c = expr.charAt(i);
if(Character.isDigit(c)) {
num = num * 10 + (c - '0');
hasNum = true;
} else {
if(!hasNum) {
throw new RuntimeException("Invalid expression");
}
numStack.push(num);
num = 0;
hasNum = false;
while(!opStack.isEmpty() && priority(opStack.peek()) >= priority(c)) {
numStack.push(applyOp(numStack.pop(), numStack.pop(), opStack.pop()));
}
opStack.push(c);
}
}
if(hasNum) {
numStack.push(num);
}
while(!opStack.isEmpty()) {
numStack.push(applyOp(numStack.pop(), numStack.pop(), opStack.pop()));
}
return numStack.pop();
}
private static long applyOp(long b, long a, char op) {
switch (op) {
case '+':
return a + b;
case '-':
return a - b;
case '*':
return a * b;
default:
throw new RuntimeException("Invalid operator");
}
}
private static int priority(char op) {
switch (op) {
case '+':
case '-':
return 1;
case '*':
return 2;
default:
return 0;
}
}
}
5.2 Python实现
import re
def extract_and_calc(s):
matches = re.findall(r'\d+(?:[-+*]\d+)*', s)
if not matches:
return 0
logest_match = max(matches, key=len)
try:
res = eval(logest_match)
return res
except:
return 0
if __name__ == '__main__':
s = input()
res = extract_and_calc(s)
print(res)