POJ 1470 (LCA離線演算法tarjan)
阿新 • • 發佈:2019-02-06
#include<iostream>
#include<string>
#include<map>
#include<cstring>
#include<cstdio>
#include<vector>
#define mm(a,b) memset(a,b,sizeof(a))
using namespace std;
const int maxn=1000;
int ask[maxn][maxn];
int ans[maxn];
int n,m;
bool visit[maxn];
bool isroot[maxn];
int father[maxn];
vector<int> v[maxn];
void init()
{
mm(visit,0);
mm(isroot,1);
mm(ans,0);
mm(ask,0);
for(int i=1;i<=n;i++)
{
v[i].clear();
father[i]=i;
}
}
int findfa(int x)
{
return x==father[x]?x:findfa(father[x]);
}
void LCA(int root)
{
for (int i=1;i<=n;i++)
if(visit[i]&&ask[root][i])
ans[findfa(i)]+=ask[root][i];
visit[root]=1;
for(int i=0,q=v[root].size();i<q;i++)
{
int tmp=v[root][i];
LCA(tmp);
father[tmp]=root;
}
}
int main()
{
while(scanf("%d",&n)!=EOF)
{
init();
int root,f,num,t;
for(int i=0;i<n;i++)
{
scanf("%d:(%d)",&f,&num);
for(int j=0;j<num;j++)
{
scanf("%d",&t);
isroot[t]=0;
v[f].push_back(t);
}
}
for(int i=1;i<=n;i++)
if(isroot[i])
{
root=i;
break;
}
scanf("%d",&m);
for(int i=0;i<m;i++)
{
int u,s;
scanf(" (%d %d)",&u,&s);
ask[u][s]++;
ask[s][u]++;
}
LCA(root);
for(int i=1;i<=n;i++)
if(ans[i])
printf("%d:%d\n",i,ans[i]);
}
return 0;
}
/*
5
5:(3) 1 4 2
1:(0)
4:(0)
2:(1) 3
3:(0)
6
(1,5) (1,4) (4,2)
(2,3)
(1,3) (4,3)
*/