拯救ice-cream(Vijos p1340)
今晚我和几个哥们一起编这道坑爹的搜索题,BFS,刚开始总是溢出,绞尽脑汁想了各种优化办法。
刚开始直接用bool判重,后来发现这样判重可能会漏掉最优解。拿了水出来的60分后,没编了,王大牛还在奋斗,我们商讨了一下判重方法,用一个记录,记录目前到这点的最短时间,这样就可以避免漏掉最优解的情况,以下是借用王大牛的程序:
1 program P1340; 2 type 3 rec=record 4 x,y:longint; 5 di:longint; 6 time:longint; 7 end; 8 var 9 s:array[1..100000,1..4] of longint; 10 time:array[1..30,1..30] of longint; 11 a:array[1..30,1..30] of char; 12 sb1,sb2:char; 13 b:array[1..30,1..30] of longint; 14 q,open,closed,t,x,y,x0,y0,x1,y1,i,j,k,l,m:longint; 15 begin 16 q:=maxlongint; 17 assign(input,'haha.in'); 18 reset(input); 19 readln(t); 20 read(x,y); 21 for j:=1 to y do 22 begin 23 read(sb1,sb2); 24 for i:=1 to x do 25 begin 26 read(a[i,j]); 27 if a[i,j]='.'then b[i,j]:=1 28 else if a[i,j]='#'then b[i,j]:=2 29 else if a[i,j]='o' then b[i,j]:=maxlongint 30 else if a[i,j]='s' then begin x0:=i;y0:=j; b[i,j]:=1;end 31 else if a[i,j]='m' then begin x1:=i;y1:=j; b[i,j]:=0;end; 32 end; 33 end; 34 close(input); 35 for j:=1 to y do 36 for i:=1 to x do 37 time[i,j]:=maxlongint; 38 closed:=0; open:=1; 39 s[1,1]:=x0; s[1,2]:=y0; s[1,3]:=0; s[1,4]:=0; 40 repeat 41 repeat 42 inc(closed); 43 if time[s[closed,1],s[closed,2]]>s[closed,4] then begin 44 time[s[closed,1],s[closed,2]]:=s[closed,4]; 45 if (s[closed,3]<>1)and(s[closed,1]<x)and(a[s[closed,1]+1,s[closed,2]]<>'o')then begin 46 inc(open); 47 s[open,1]:=s[closed,1]+1; 48 s[open,2]:=s[closed,2]; 49 s[open,3]:=3; 50 s[open,4]:=s[closed,4]+b[s[closed,1],s[closed,2]]; 51 end; 52 if a[s[open,1],s[open,2]]='m' then break; 53 if (s[closed,3]<>3)and(s[closed,1]>1)and(a[s[closed,1]-1,s[closed,2]]<>'o') then begin 54 inc(open); 55 s[open,1]:=s[closed,1]-1; 56 s[open,2]:=s[closed,2]; 57 s[open,3]:=1; 58 s[open,4]:=s[closed,4]+b[s[closed,1],s[closed,2]]; 59 end; 60 if a[s[open,1],s[open,2]]='m' then break; 61 if (s[closed,3]<>0)and(s[closed,2]>1)and(a[s[closed,1],s[closed,2]-1]<>'o') then begin 62 inc(open); 63 s[open,1]:=s[closed,1]; 64 s[open,2]:=s[closed,2]-1; 65 s[open,3]:=2; 66 s[open,4]:=s[closed,4]+b[s[closed,1],s[closed,2]]; 67 end; 68 if a[s[open,1],s[open,2]]='m' then break; 69 if (s[closed,3]<>2)and(s[closed,2]<y)and(a[s[closed,1],s[closed,2]+1]<>'o') then begin 70 inc(open); 71 s[open,1]:=s[closed,1]; 72 s[open,2]:=s[closed,2]+1; 73 s[open,3]:=0; 74 s[open,4]:=s[closed,4]+b[s[closed,1],s[closed,2]]; 75 end; 76 if a[s[open,1],s[open,2]]='m' then break; 77 end; 78 until (a[s[open,1],s[open,2]]='m')or(closed=open); 79 if q>s[open,4] then q:=s[open,4]; 80 until (closed=open); 81 if q>=t then write('55555') 82 else 83 write(q); 84 end.
大概就是BFS,然后判重,没什么别的技巧,憋了几个小时总算是憋出了100分,惭愧啊惭愧!
By ZYT
12.10.05
仙人抚我顶,结发受长生