CF195C Try and Catch 题解
洛谷题面 | Codeforces 题面
因为洛谷爬虫太逊了,你需要注意到样例输入输出里面异常显示了 ",请在测样例的时候把它们换成 "。
这道题很有意思,题目让我们实现一个 try-catch 处理程序。给定的这个程序里面只会执行一次 throw 抛出异常,我们需要确定哪一个 catch 语句捕获到了这个异常(若没有输出 Unhandled Exception)。
首先,我们开一个栈存储每一个 try 语句的位置(以便在遇到 catch 时找到对应的 try),之后定义一个字符串和一个整数代表抛出异常的名称和位置。
| stack<int> st;
string ts;
int tp;
|
读入每一行时,我们判断当前读入的语句是哪种类型:
try:将当前行号压入栈。
throw:更新一下抛出异常的名称和位置。
catch:读取栈顶元素(对应的 try 语句的位置),若:
try 语句在抛出异常位置之前,且当前 catch 的名称与抛出的异常名称匹配:输出 catch 定义的输出内容,程序结束。
- 否则,程序继续。
| // 珍爱账号,请勿贺题
#include <bits/stdc++.h>
using namespace std;
#define int long long
int n,tp;
string s,ts;
stack<int>st;
// 1-try 2-catch 3-throw //
int func_type(){
for(int i=0;i<s.length();i++){
if(s.substr(i,3)=="try")return 1;
if(s.substr(i,5)=="catch")return 2;
if(s.substr(i,5)=="throw")return 3;
}
return -1;
}
string func_arg(bool is_last=0){
string res="";
// find 找元素,没找到返回 -1,找到返回位置,故判断是否找到时将返回值 +1 再转换为 bool 即可。
int a=s.find("("),b=s.find(is_last?")":",");
if(a+1&&b+1){
for(int i=a+1;i<b;i++){
if(s[i]!=' ')res+=s[i];
}
}
return res;
}
void func_print(){
int a=s.find("\""),b=s.rfind("\"");
if(a+1&&b+1){
for(int i=a+1;i<b;i++){
cout<<s[i];
}
cout<<endl;
}
}
void solve(){
cin>>n;
getline(cin,s); // 吃个换行先
for(int i=1;i<=n;i++){
getline(cin,s);
int p=func_type();
if(p==1){
st.push(i);
} else if(p==2) {
int pp=st.top();
st.pop();
if(tp>pp && func_arg()==ts){
func_print();
return;
}
} else if(p==3) {
ts = func_arg(1);
tp = i;
}
}
cout<<"Unhandled Exception"<<endl;
}
int32_t main(){
ios::sync_with_stdio(0);
cin.tie(0);
solve();
return 0;
}
|