CD操作

来源:互联网 发布:手机打印机软件 编辑:程序博客网 时间:2024/06/05 22:32
#include<cstdio>#include<cstring>#include<algorithm>#include<vector>#include<iostream>#include<string>#include<map>using namespace std;typedef __int64 lld;const int maxn=100005;int n,m;int dp[maxn][18];vector<int>edge[maxn];map<string,int>mp;string s1,s2;int tot;int root;int deep[maxn];void dfs(int u,int f,int dep){int i;deep[u]=dep;dp[u][0]=f;for(i=1;i<18;i++){dp[u][i]=dp[dp[u][i-1]][i-1];}for(i=0;i<edge[u].size();i++){dfs(edge[u][i],u,dep+1);}}int Ancestor(int x,int len){for(int i=17;i>=0;i--){if(len>=1<<i){len-=1<<i;x=dp[x][i];}}return x;}int LCA(int x,int y){if(deep[x]>deep[y])x=Ancestor(x,deep[x]-deep[y]);elsey=Ancestor(y,deep[y]-deep[x]);if(x==y)return x;int ret=root;int i=17;while(i--){if(dp[x][i]==dp[y][i]){ret=dp[x][i];}else{x=dp[x][i];y=dp[y][i];}}return ret;}int main(){int i,j;int T;int a,b;int u,v;scanf("%d",&T);while(T--){scanf("%d %d",&n,&m);tot=1;for(i=0;i<maxn;i++)edge[i].clear();mp.clear();for(i=1;i<n;i++){cin>>s1>>s2;if(mp.find(s1)==mp.end()){a=tot;mp[s1]=tot++;}elsea=mp[s1];if(mp.find(s2)==mp.end()){b=tot;mp[s2]=tot++;}elseb=mp[s2];edge[b].push_back(a);deep[a]=1;}for(i=1;i<tot;i++){if(!deep[i])root=i;}memset(dp,0,sizeof(dp));dfs(root,0,0);for(i=1;i<=m;i++){cin>>s1>>s2;a=mp[s1];b=mp[s2];int ff=LCA(a,b);int ans=deep[a]-deep[ff]+(b!=ff);printf("%d\n",ans);}}return 0;}

原创粉丝点击