這題之前數據結構作業做過,寫的好像挺麻煩的,比賽時也沒功夫寫,今天靜下心來倒是想了個不錯的方法,無BUG 1A
#include <cstdio>
#include <cstring>
#include <algorithm>
#include <iostream>
#include <string>
#include <set>
#include <vector>
#include <map>
#include <sstream>
#define LL long long
const LL INF = 0x3f3f3f3f;
const int maxn = 200000 + 5;
using namespace std;
int fa[maxn];
int a[maxn];
map<string,int> maps;
string s;
vector<int> vec[maxn];
bool dfs(int f, int son){
if(vec[f].size() == 0)
return false;
for(int i=0; i<vec[f].size(); i++){
if(vec[f][i] == son) return true;
if(dfs(vec[f][i],son)) return true;
}
return false;
}
bool solve(string name1, string name2, string op){
int id1 = maps[name1];
int id2 = maps[name2];
if(op == "child")
return fa[id1] == id2;
if(op == "ancestor")
return dfs(id1,id2);
if(op == "sibling")
return fa[id1] == fa[id2];
if(op == "parent")
return fa[id2] == id1;
if(op == "descendant")
return dfs(id2,id1);
return false;
}
int main(){
int cnt = 0, deep, j;
int n,q;
string name;
cin >> n >> q;
getchar();
for(int i=0; i<n; i++){
deep = 0;
getline(cin,s);
int len = (int)s.length();
for(j=0; j<len; j++){
if(s[j] == ' ') deep++;
else break;
}
name = s.substr(j,len-j);
maps[name] = cnt++;
int id = maps[name];//該串的序號
deep /= 2;
int turn = a[deep];//此時的父親
if(id != 0){
vec[turn].push_back(id);
fa[id] = turn;
}
else fa[id] = -1;
a[deep+1] = id;//更新當前層數的父親
}
string x;
while(q--){
string name1, name2, judge, temp;
cin >> name1 >> temp >> temp >> judge >> temp >> name2;
if(solve(name1,name2,judge)) cout << "True" << endl;
else cout << "False" << endl;
}
}