bzoj 1912: [Apio2010]patrol 巡逻
Posted ws_ccd
tags:
篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了bzoj 1912: [Apio2010]patrol 巡逻相关的知识,希望对你有一定的参考价值。
呵呵呵呵呵呵,自己画图,大概半个小时,觉的连上边会成环(是不是该交仙人掌了??)然后求环不重合部分最大就好了,
结果写了一坨DP,最后写不下去了,再次扒了题解。
发现我真的是个sb。
k==1,直接是直径
k==2,搞出直径然后把直径删掉(把权值赋为-1,再找直径)(有点像我一开始想的每次找个最长链去贪心,然而,,总觉得,这种题贪心这么可能对)
1 /*#include <bits/stdc++.h> 2 #define LL long long 3 #define lowbit(x) x&(-x) 4 #define inf 0x3f3f3f3f 5 #define N 100005 6 using namespace std; 7 inline int ra() 8 { 9 int x=0,f=1; char ch=getchar(); 10 while (ch<‘0‘ || ch>‘9‘) {if (ch==‘-‘) f=-1; ch=getchar();} 11 while (ch>=‘0‘ && ch<=‘9‘) {x=x*10+ch-‘0‘; ch=getchar();} 12 return x*f; 13 } 14 int head[N],cnt,n,f[N][3][3],k; 15 struct edge{int next,to;}e[N<<1]; 16 void insert(int x, int y){e[++cnt].next=head[x]; e[cnt].to=y; head[x]=cnt;} 17 void dfs(int x, int fa) 18 { 19 int mx1=0,mx2=0,mx3=0,mx4=0; 20 for (int i=head[x];i;i=e[i].next) 21 { 22 if (e[i].to==fa) continue; 23 dfs(e[i].to,x); 24 int orz=f[e[i].to][0][1],flag=1,hehe=1; 25 if (orz<=mx1 && orz<=mx2 && orz<=mx3 && orz>mx4) mx4=orz; 26 if (orz<=mx1 && orz<=mx2 && orz>mx3) mx4=mx3,mx3=orz; 27 if (orz<=mx1 && orz>mx2) mx4=mx3,mx3=mx2,mx2=orz,hehe=0; 28 if (orz>mx1) mx4=mx3,mx3=mx2,mx2=mx1,mx1=orz,flag=0; 29 if (f[x][1][1] && k) 30 { 31 if (!flag) 32 f[x][2][0]=max(f[x][2][0],f[x][1][1]+mx1+1); 33 else if (!hehe) f[x][2][0]=max(f[x][2][0],f[x][1][1]+mx2+1); 34 } 35 cout<<f[x][1][1]<<endl; 36 if (f[x][1][0] && k) f[x][1][1]=max(f[x][1][1],f[x][1][0]+mx1+1); 37 cout<<f[x][1][1]<<endl; 38 if (f[e[i].to][1][0] && mx2 && k) f[x][1][1]=max(f[x][1][1],1+f[e[i].to][1][0]+flag?mx1:mx2); 39 if (f[e[i].to][1][1] && k) f[x][1][1]=max(f[x][1][1],f[e[i].to][1][1]+1); 40 if (f[e[i].to][1][1] && mx2 && k) f[x][2][0]=max(f[x][2][0],1+f[e[i].to][1][1]+flag?mx1:mx2); 41 if (f[e[i].to][2][0] && k) f[x][2][0]=max(f[x][2][0],f[e[i].to][2][0]); 42 if (f[x][1][0] && f[e[i].to][1][0] && k) f[x][2][0]=max(f[x][2][0],f[x][1][0]+f[e[i].to][1][0]); 43 f[x][1][0]=max(f[x][1][0],max(mx1+mx2+1,f[e[i].to][1][0])); 44 f[x][0][1]=mx1+1; 45 if (f[3][1][1]==3) {cout<<x<<" "<<e[i].to; while (1);} 46 } 47 printf("%d %d %d %d %d\n",x,f[x][0][1],f[x][1][0],f[x][1][1],f[x][2][0]); system("pause"); 48 } 49 int main(int argc, char const *argv[]) 50 { 51 n=ra(); k=ra(); k--; 52 for (int i=1; i<n; i++) 53 { 54 int x=ra(),y=ra(); 55 insert(x,y); insert(y,x); 56 } 57 dfs(1,0); 58 printf("%d\n",n*2-f[1][k+1][0]); 59 return 0; 60 }*/ 61 #include <bits/stdc++.h> 62 #define LL long long 63 #define lowbit(x) x&(-x) 64 #define inf 0x3f3f3f3f 65 #define N 100005 66 using namespace std; 67 inline int ra() 68 { 69 int x=0,f=1; char ch=getchar(); 70 while (ch<‘0‘ || ch>‘9‘) {if (ch==‘-‘) f=-1; ch=getchar();} 71 while (ch>=‘0‘ && ch<=‘9‘) {x=x*10+ch-‘0‘; ch=getchar();} 72 return x*f; 73 } 74 int mx,n,k,tot,cnt=1,len; 75 int head[N]; 76 int s1[N],s2[N]; 77 struct edge{ 78 int to,next,v; 79 }e[N<<1]; 80 void insert(int x, int y){ 81 e[++cnt].next=head[x]; e[cnt].to=y; e[cnt].v=1; head[x]=cnt; 82 } 83 int dfs(int x, int fa) 84 { 85 int mx1=0,mx2=0; 86 for (int i=head[x];i;i=e[i].next) 87 { 88 if (e[i].to==fa) continue; 89 int v=e[i].v+dfs(e[i].to,x); 90 if (v>mx1) mx2=mx1,mx1=v,s2[x]=s1[x],s1[x]=i; 91 else if (v>mx2) mx2=v,s2[x]=i; 92 } 93 if (mx1+mx2>len) len=mx1+mx2,mx=x; 94 return mx1; 95 } 96 int main(int argc, char const *argv[]) 97 { 98 n=ra(); k=ra(); tot=2*(n-1); 99 for (int i=1; i<n; i++) 100 { 101 int x=ra(),y=ra(); 102 insert(x,y); 103 insert(y,x); 104 } 105 dfs(1,0); tot-=len-1; 106 if (k==2) 107 { 108 len=0; 109 for (int i=s1[mx];i;i=s1[e[i].to]) e[i].v=e[i^1].v=-1; 110 for (int i=s2[mx];i;i=s1[e[i].to]) e[i].v=e[i^1].v=-1; 111 dfs(1,0); tot-=len-1; 112 } 113 cout<<tot; 114 return 0; 115 }
以上是关于bzoj 1912: [Apio2010]patrol 巡逻的主要内容,如果未能解决你的问题,请参考以下文章
bzoj 1912 : [Apio2010]patrol 巡逻 树的直径