bzoj1001 [BeiJing2006]狼抓兔子
1001: [BeiJing2006]狼抓兔子
Time Limit: 15 Sec Memory Limit: 162 MBSubmit: 19687 Solved: 4870
[Submit][Status][Discuss]
Description
现在小朋友们最喜欢的"喜羊羊与灰太狼",话说灰太狼抓羊不到,但抓兔子还是比较在行的,
而且现在的兔子还比较笨,它们只有两个窝,现在你做为狼王,面对下面这样一个网格的地形:
左上角点为(1,1),右下角点为(N,M)(上图中N=4,M=5).有以下三种类型的道路
1:(x,y)<==>(x+1,y)
2:(x,y)<==>(x,y+1)
3:(x,y)<==>(x+1,y+1)
道路上的权值表示这条路上最多能够通过的兔子数,道路是无向的. 左上角和右下角为兔子的两个窝,
开始时所有的兔子都聚集在左上角(1,1)的窝里,现在它们要跑到右下解(N,M)的窝中去,狼王开始伏击
这些兔子.当然为了保险起见,如果一条道路上最多通过的兔子数为K,狼王需要安排同样数量的K只狼,
才能完全封锁这条道路,你需要帮助狼王安排一个伏击方案,使得在将兔子一网打尽的前提下,参与的
狼的数量要最小。因为狼还要去找喜羊羊麻烦.
Input
第一行为N,M.表示网格的大小,N,M均小于等于1000.
接下来分三部分
第一部分共N行,每行M-1个数,表示横向道路的权值.
第二部分共N-1行,每行M个数,表示纵向道路的权值.
第三部分共N-1行,每行M-1个数,表示斜向道路的权值.
输入文件保证不超过10M
Output
输出一个整数,表示参与伏击的狼的最小数量.
Sample Input
3 4
5 6 4
4 3 1
7 5 3
5 6 7 8
8 7 6 5
5 5 5
6 6 6
5 6 4
4 3 1
7 5 3
5 6 7 8
8 7 6 5
5 5 5
6 6 6
Sample Output
14
题解
平面图最大流……周冬论文里说的很清楚了……贴一下代码吧……
1 /************************************************************** 2 Problem: 1001 3 User: 1090900715 4 Language: Pascal 5 Result: Accepted 6 Time:7744 ms 7 Memory:103760 kb 8 ****************************************************************/ 9 10 program j01; 11 const maxn=2000086; 12 var b:array[0..1000,0..1000,0..1]of longint; 13 q,next,data:array[0..6000086]of longint; 14 dis,head,l:array[0..maxn]of longint; 15 inl:array[0..maxn]of boolean; 16 n,m,x,i,j,tt,tot:longint; 17 18 procedure add(u,v,w:longint); 19 begin 20 inc(tt); 21 q[tt]:=v; 22 next[tt]:=head[u]; 23 head[u]:=tt; 24 data[tt]:=w; 25 end; 26 27 procedure spfa; 28 var h,tail,i,j:longint; 29 begin 30 fillchar(dis,sizeof(dis),$3f); 31 fillchar(inl,sizeof(inl),0); 32 dis[0]:=0;h:=0;tail:=1;l[1]:=0;inl[0]:=true; 33 while h<>tail do 34 begin 35 inc(h);if h>maxn then h:=1; 36 i:=l[h]; 37 j:=head[i]; 38 while j>0 do 39 begin 40 if dis[i]+data[j]<dis[q[j]] then 41 begin 42 dis[q[j]]:=dis[i]+data[j]; 43 if inl[q[j]]=false then 44 begin 45 inc(tail);if tail>maxn then tail:=1; 46 l[tail]:=q[j]; 47 inl[q[j]]:=true; 48 end; 49 end; 50 j:=next[j]; 51 end; 52 inl[i]:=false; 53 end; 54 end; 55 56 begin 57 readln(n,m); 58 tot:=0; 59 for i:=1 to n-1 do 60 for j:=1 to m-1 do 61 begin 62 inc(tot); 63 b[i,j,0]:=tot; 64 inc(tot); 65 b[i,j,1]:=tot; 66 end; 67 inc(tot); 68 fillchar(head,sizeof(head),0); 69 tt:=0; 70 for i:=1 to n do 71 for j:=1 to m-1 do 72 begin 73 read(x); 74 if i=1 then add(b[i,j,1],tot,x); 75 if i=n then 76 add(0,b[i-1,j,0],x); 77 if (i<>1)and(i<>n) then 78 begin 79 add(b[i,j,1],b[i-1,j,0],x); 80 add(b[i-1,j,0],b[i,j,1],x); 81 end; 82 end; 83 for i:=1 to n-1 do 84 for j:=1 to m do 85 begin 86 read(x); 87 if j=1 then 88 add(0,b[i,j,0],x); 89 if j=m then add(b[i,j-1,1],tot,x); 90 if (j<>1)and(j<>m) then 91 begin 92 add(b[i,j,0],b[i,j-1,1],x); 93 add(b[i,j-1,1],b[i,j,0],x); 94 end; 95 end; 96 for i:=1 to n-1 do 97 for j:=1 to m-1 do 98 begin 99 read(x); 100 add(b[i,j,0],b[i,j,1],x); 101 add(b[i,j,1],b[i,j,0],x); 102 end; 103 spfa; 104 writeln(dis[tot]); 105 end. 106