题目
感觉这题拿国二难度很大啊,要不是我做过这个L3-1,我这把都拿不了。可能是模型建立能力不太够叭。L1-8也很恶心,敲了半天。冰岛人那个我着实没想到那个情况。
l2-2冰岛人
坑点: 如果a和b的LCA,是a的第三代同时是b的第六代,好寄。因为题干要求LCA要>=任何一方的深度+4.按我原来的搜索方法是判断不出来的,我把各自深度4以内的节点计数++,>1说明是LCA,但是遇到3、6代就搜不出来,误以为正确。所以应该暴力地枚举两个点的深度差4以内的父节点,判断LCA是否对于a或者b深度差<=4。
!需要开unorder_map,不然T一个点。其实可以按题解写法,string对应一个结构体node,可以少调用几次map,涨知识了,当然也可以用哈希map。
代码:
#include<bits/stdc++.h>
using namespace std;
const int N = 1e5+10;
typedef long long ll;
int n,m,k,T;
map<string,string> mp; //父节点
map<string,int> to; //1:男
map<string,int> vis;
bool flag;
void dfs(string a,string b)
{
int i = 1,j = 1;
for(string x = a;x.size();++i,x = mp[x])
{
j = 1;
for(string y = b;y.size();++j,y = mp[y])
{
if(i>=5&&j>=5) break;
if(x==y&&(i<5||j<5))
{
flag = 0;
return ;
}
}
}
flag = 1;
}
void solve()
{
cin>>n;
while(n--)
{
string a,b; cin>>a>>b;
vis[a] = 1;
if(b.back() == 'n')
{
string s = b.substr(0,b.size()-4);
mp[a] = s;
to[a] = to[s] = vis[s] = 1;
}
else if(b.back() == 'r')
{
string s = b.substr(0,b.size()-7);
mp[a] = s;
to[s] = vis[s] = 1;
}
else if(b.back() == 'm')
{
to[a] = 1;
}
}
cin>>m;
while(m--)
{
string a,b,x,y; cin>>a>>x>>b>>y;
if(!vis[a] || !vis[b])
{
cout<<"NA";
}
else
{
if(to[a] == to[b])
{
cout<<"Whatever";
}
else
{
dfs(a,b);
if(flag) cout<<"Yes";
else cout<<"No";
}
}
cout<<"\n";
}
}
signed main(void)
{
ios::sync_with_stdio(false),cin.tie(0),cout.tie(0);
solve();
return 0;
}
L1-8有点恶心人,敲了半小时,处理字符串,太麻烦了 。
L3-1地铁一日游和L3-2计算图也很难,一个要想到floyd对于每个点新建一个题干描述的图,另一个则需要想到递归求,而且懂点数学基础。