题目描述
假设一个表达式有英文字母(小写)、运算符(+,—,*,/)和左右小(圆)括号构成,以“@”作为表达式的结束符。请编写一个程序检查表达式中的左右圆括号是否匹配,若匹配,则返回“YES”;否则返回“NO”。表达式长度小于255,左圆括号少于20个。
输入格式
一行:表达式
输出格式
一行:“YES” 或“NO”
输入输出样例
输入 #1复制
2*(x+y)/(1-x)@
输出 #1复制
YES
输入 #2复制
(25+x)*(a*(a+b+b)@
输出 #2复制
NO
来自 <https://www.luogu.com.cn/problem/P1739?contestId=46635>
YES | |||
(25+x)*(a*(a+b+b)@
消去 | |||||||||
No | |||||||||
接下来放下源码:
import java.io.*;
import java.util.Stack;
/**
* 注意情况:
* 全是))))或全是((((
* 原理:
* 可以用计数法,若左右括号数量相同即为YES
* 也可以“栈消去“法,将char不断加入stack中,遇到()则消去,直到消为0为YES
*/
public class 表达式括号匹配 {
public static void main(String[] args) throws IOException {
BufferedReader re = new BufferedReader(new InputStreamReader(System.in));
//StreamTokenizer r = new StreamTokenizer(new BufferedReader(new InputStreamReader(System.in)));
PrintWriter pr = new PrintWriter(new OutputStreamWriter(System.out));
Stack stack = new Stack();
String x = re.readLine();//输入字符串
//flag用来记录)前面是否有 (
//遇见“(”压入栈中;遇到“)”先判断栈中先前是否有“(”,若有压栈,然后讲一对“()”弹出栈中
//flag为true栈中有“(”,false栈中无“(”
boolean flag = false;
for (int i = 0; i < x.length(); i++) {
char tempCharacter = x.charAt(i);
if (tempCharacter == '(') {
stack.push(tempCharacter);
flag = true;
} else if (tempCharacter == ')') {
if (flag == false) {
stack.push(tempCharacter);
} else {//消去过程
stack.push(tempCharacter);
stack.pop();
stack.pop();
if (stack.empty()) {
flag = false;
} else {
char e = (char) stack.peek();
if (e == '(') {
flag = true;
} else {
flag = false;
}
}
}
} else if (tempCharacter == '@') {
break;
}
}
if (stack.empty()) {//若最终栈为空,即对应的“()”均已匹配,为YES
pr.println("YES");
pr.flush();
} else {
pr.println("NO");
pr.flush();
}
}
}