【VIJOS】P1037 搭建双塔
f[i-1,t] →把h[i]给了f[i-1,t]后 f[i-1,t]+h[i]=f[i,j]+j; 原低塔变高塔
现低塔高度→(f[i-1,t]+t)< 现高塔高度→ f[i-1,t]+h[i] (t<h[i])
→f[i,h[i]]
→j=h[i]-t t=h[i]-j;
f[i-1,t] → 后 f[i-1,t]+h[i]=f[i,j] 原低塔还是低塔 h[i]<t
f[i-1,t] →把h[i]给f[i-1,t]+t → f[i-1,j-h[i]]=f[i,j]
f[i-1,t]+h[i]=f[i,j]
现低塔:f[i-1,t]+h[i]; 现高塔 f[i-1,t]+t
j=t-h[i] t=j+h[i]
h[i]<j+h[i]
1 const null=32767; 2 var 3 n,m,max1,i,j,t:integer; 4 h:array[1..100] of integer; 5 f:array[0..100,0..2000] of integer; 6 function max(a,b:integer):integer; 7 begin 8 if a=null then exit(b); 9 if b=null then exit(a); 10 if (a>b) then exit(a); 11 exit(b); 12 end; 13 begin 14 assign(input,'P1037.in'); 15 reset(input); 16 assign(output,'P1037.out'); 17 rewrite(output); 18 readln(n); 19 for i:=0 to n do 20 for j:=0 to 2000 do 21 f[i,j]:=null; 22 for i:=1 to n do read(h[i]); 23 f[0,0]:=0; 24 for i:=1 to n do 25 for j:=2000 downto 0 do 26 begin 27 if f[i-1,j]<>null then f[i,j]:=f[i-1,j]; 28 if j>=h[i] then if f[i-1,j-h[i]]<>null then f[i,j]:=max(f[i-1,j-h[i]],f[i,j]); // h[i] was given to the higher one 29 30 //next:give to the lower one 31 if h[i]-j>=0 then 32 begin 33 if f[i-1,h[i]-j]<>null then f[i,j]:=max(f[i-1,h[i]-j]+h[i]-j,f[i,j]); 34 end; 35 begin 36 if f[i-1,j+h[i]]<>null then f[i,j]:=max(f[i-1,j+h[i]]+h[i],f[i,j]); 37 end; 38 39 end; 40 41 {for i:=0 to n do 42 begin 43 for j:=0 to 15 do write(f[i,j]:6); 44 writeln; 45 end; } 46 if f[n,0]<>0 then writeln(f[n,0]) else writeln('Impossible'); 47 close(input); 48 close(output); 49 end.