社区讨论
虚树30分WA+AC+TLE,求调
P4103[HEOI2014] 大工程参与者 2已保存回复 2
讨论操作
快速查看讨论及其快照的属性,并进行相关操作。
- 当前回复
- 2 条
- 当前快照
- 1 份
- 快照标识符
- @mi3yj0ue
- 此快照首次捕获于
- 2025/11/18 10:31 4 个月前
- 此快照最后确认于
- 2025/11/18 10:31 4 个月前
CPP
#include<bits/stdc++.h>
using namespace std;
#define int long long
const int N=8000010;
int n,q,k,a[N],uu,vv,hea[N],edge[N],nxt[N],cnt;
int he[N],eg[N],nx[N],cnt1;
int son[N],siz[N],idx,id[N],fa[N],tot[N],dep[N];
void add(int u,int v){edge[++cnt]=v,nxt[cnt]=hea[u],hea[u]=cnt;return ;}
void add1(int u,int v){eg[++cnt1]=v,nx[cnt1]=he[u],he[u]=cnt1;return ;}
void dfs1(int now,int p){
siz[now]=1,fa[now]=p,dep[now]=dep[p]+1,id[now]=++idx;
for(int jj=hea[now];jj;jj=nxt[jj]){
int to=edge[jj];
if(to==p) continue;
dfs1(to,now);
siz[now]+=siz[to];
if(siz[son[now]]<siz[to]) siz[now]=to;
}
return ;
}
void dfs2(int now,int p){
tot[now]=p;
if(son[now]) dfs2(son[now],p);
for(int jj=hea[now];jj;jj=nxt[jj]){
int to=edge[jj];
if(to==fa[now]||to==son[now]) continue;
dfs2(to,to);
}
return ;
}
int lca(int x,int y){
while(tot[x]!=tot[y]){
if(dep[tot[x]]<dep[tot[y]]) swap(x,y);
x=fa[tot[x]];
}
return dep[x]<dep[y]?x:y;
}
bool cmp(int x,int y){return id[x]<id[y];}
int st[N],to1,si[N];
bool pd[N];
void build(){
sort(a+1,a+k+1,cmp);
st[to1=1]=1;
if(a[1]!=1) st[++to1]=a[1];
for(int j=2;j<=k;++j){
int l=lca(st[to1],a[j]);
while(to1>1&&dep[l]<=dep[st[to1-1]]){
add1(st[to1-1],st[to1]),--to1;
}
if(l!=st[to1]){
add1(l,st[to1]),st[to1]=l;
}
st[++to1]=a[j];
}
while(to1){
add1(st[to1-1],st[to1]),--to1;
}
return ;
}
int dpmin[N],dpmax[N],cou[N],dpans[N],ans1,ans2,ans3;
void dfs3(int now){
if(pd[now]) dpmin[now]=0,dpmax[now]=0;
for(int jj=he[now];jj;jj=nx[jj]){
int to=eg[jj];
dfs3(to);
ans2=max(dpmax[to]+dep[to]-dep[now]+dpmax[now],ans2);
dpmax[now]=max(dpmax[now],dpmax[to]+dep[to]-dep[now]);
ans1=min(dpmin[to]+dep[to]-dep[now]+dpmin[now],ans1);
dpmin[now]=min(dpmin[now],dpmin[to]+dep[to]-dep[now]);
}
return ;
}
void dfs5(int now){
if(pd[now]||now==1) si[now]=1;
dpans[now]=0;
for(int jj=he[now];jj;jj=nx[jj]){
int to=eg[jj];
dfs5(to);
dpans[to]+=si[to]*(dep[to]-dep[now]);
ans3+=dpans[to]*si[now]+dpans[now]*si[to];
dpans[now]+=dpans[to];
si[now]+=si[to];
}
dpmin[now]=2e17,dpmax[now]=-2e17,he[now]=0;
return ;
}
signed main(){
ios::sync_with_stdio(0);cin.tie(0);cout.tie(0);
cin>>n;
for(int i=1;i<=n;++i) dpmax[i]=-2e17,dpmin[i]=2e17;
for(int i=1;i<n;++i){
cin>>uu>>vv;
add(uu,vv),add(vv,uu);
}
dfs1(1,0),dfs2(1,1);
cin>>q;
for(int i=1;i<=q;++i){
ans1=2e17,ans2=-2e17,ans3=0;
cin>>k;
for(int j=1;j<=k;++j){
cin>>a[j];
pd[a[j]]=1;
}
build();
dfs3(1);
dfs5(1);
if(!pd[1]) ans3-=dpans[1];
cout<<ans3<<' '<<ans1<<' '<<ans2<<'\n';
for(int j=1;j<=k;++j) pd[a[j]]=0;
}
return 0;
}
回复
共 2 条回复,欢迎继续交流。
正在加载回复...