[BZOJ1791][IOI2008]Island岛屿(环套树DP)

同NOI2013快餐店(NOI出原题?),下面代码由于BZOJ栈空间过小会RE。

大致是对每个连通块找到环,在所有内向树做一遍DP,再在环上做两遍前缀和优化的DP。

 1 #include<cstdio>
 2 #include<cstring>
 3 #include<iostream>
 4 #include<algorithm>
 5 #define rep(i,l,r) for (int i=(l); i<=(r); i++)
 6 #define For(i,x) for (int i=h[x],k; i; i=nxt[i])
 7 typedef long long ll;
 8 using namespace std;
 9 
10 const int N=1000010;
11 ll ans,res,f[N],v1[N],v2[N],u1[N],u2[N];
12 int dfn[N],fa[N],pre[N],h[N],a[N],b[N];
13 int n,x,w,cnt,tim,tot,to[N<<1],val[N<<1],nxt[N<<1],d[N];
14 void add(int u,int v,int w){ to[++cnt]=v; val[cnt]=w; nxt[cnt]=h[u]; h[u]=cnt; }
15 
16 void dfs(int x){
17     dfn[x]=++tim;
18     For(i,x) if ((k=to[i])!=fa[x]){
19         if (!dfn[k]) fa[k]=x,pre[k]=val[i],dfs(k);
20         else if (dfn[k]>dfn[x]){
21             for (int t=k; t!=x; t=fa[t]) a[++tot]=t,d[t]=1,b[tot]=pre[t];
22             a[++tot]=x; d[x]=1; b[tot]=val[i];
23         }
24     }
25 }
26 
27 void Dfs(int x,int fa){
28     For(i,x) if ((k=to[i])!=fa && !d[k])
29         Dfs(k,x),ans=max(ans,f[x]+f[k]+val[i]),f[x]=max(f[x],f[k]+val[i]);
30 }
31 
32 void DP(int x){
33     tot=0; ans=0; dfs(x); ll sm=0,mx=0;
34     rep(i,1,tot) Dfs(a[i],0);
35     rep(i,1,tot) d[a[i]]=0;
36     rep(i,0,tot+1) u1[i]=u2[i]=v1[i]=v2[i]=0;
37     rep(i,1,tot){
38         sm+=b[i-1]; u1[i]=max(u1[i-1],f[a[i]]+sm);
39         v1[i]=max(v1[i-1],f[a[i]]+sm+mx); mx=max(mx,f[a[i]]-sm);
40         ans=max(ans,v1[i]);
41     }
42     int tmp=b[tot]; sm=mx=b[tot]=0;
43     for (int i=tot; i; i--){
44         sm+=b[i]; u2[i]=max(u2[i+1],f[a[i]]+sm);
45         v2[i]=max(v2[i+1],f[a[i]]+sm+mx); mx=max(mx,f[a[i]]-sm);
46         ans=max(ans,v2[i]);
47     }
48     rep(i,1,tot-1) ans=max(ans,u1[i]+u2[i+1]+tmp);
49     res+=ans;
50 }
51 
52 int main(){
53     freopen("bzoj1791.in","r",stdin);
54     freopen("bzoj1791.out","w",stdout);
55     scanf("%d",&n);
56     rep(i,1,n) scanf("%d%d",&x,&w),add(x,i,w),add(i,x,w);
57     rep(i,1,n) if (!dfn[i]) DP(i);
58     printf("%lld\n",res);
59     return 0;
60 }

 

posted @ 2018-11-08 21:30  HocRiser  阅读(259)  评论(0编辑  收藏  举报