题解:P10406 「SMOI-R1」Company
首先,假设将一个公司看成一个“大点”,则连接最后的“大树”每个点度数最多为
这里有两种情况:一是一条链,二是两条链通过一个公司连接在一起。
对于第一种情况,又有最顶是
对于第二种情况,枚举“大树”的根
讲的有点抽象,放个丑陋的代码:
int n,ans,mx1,mx2,mx3,x,y,d1[M],d2[M],mx[N],dmx[N]; vi G1[M],G2[M];
struct Tree {
int m; vi dep,dep2; vector<vi> G;
void dfs(int u,int fa=0) {for(int v:G[u]) if(v!=fa) dep[v]=dep[u]+1,dfs(v,u);}
void rdfs(int u,int fa=0) {for(int v:G[u]) if(v!=fa) dep2[v]=dep2[u]+1,rdfs(v,u);}
}T[N];
void dfs1(int u,int fa=0) {for(int v:T[1].G[u]) if(v!=fa) {d1[v]=d1[u]+1; if(v!=1&&T[1].G[v].size()<=1) mx1=max(mx1,d1[v]); dfs1(v,u);}}
void dfs2(int u,int fa=0) {for(int v:T[2].G[u]) if(v!=fa) {d2[v]=d2[u]+1; if(v!=1&&T[2].G[v].size()<=1) mx2=max(mx2,d2[v]); dfs2(v,u);}}
void QwQ() {
n=rd(),ans=n-1,mx3=-INF;
for(int i=1;i<=n;i++) {
T[i].m=rd(),T[i].G.resize(T[i].m+1),T[i].dep.resize(T[i].m+1),T[i].dep2.resize(T[i].m+1);
for(int j=2,x;j<=T[i].m;j++) x=rd(),T[i].G[x].pb(j),T[i].G[j].pb(x);
}
x=rd(),y=rd(),dfs1(x),dfs2(y);
for(int i=1,s;i<=n;i++) {
T[i].dfs(1),s=-1;
for(int j=2;j<=T[i].m;j++) if(T[i].dep[j]>=mx[i]&&T[i].G[j].size()==1) mx[i]=T[i].dep[j],s=j;
if(i>2) ans+=mx[i];
if(!~s) continue; T[i].rdfs(s);
for(int j=2;j<=T[i].m;j++) if(T[i].G[j].size()==1) dmx[i]=max(dmx[i],T[i].dep2[j]);
}
for(int i=1;i<=n;i++) mx3=max(mx3,dmx[i]-mx[i]);
wr(max(ans+max(d1[1]+mx2,d2[1]+mx1),mx3!=-INF?ans+mx3+d1[1]+d2[1]:0),"\n");
}