Description
After the brave Druifario had accomplished his task well, he was rapidly retreating to his base. But because there was a large group of pursuers behind him, Fario had to return to his base as soon as possible, otherwise he would be caught by the enemy.
Finally, Fario arrived at the last stop: the Terrachel Wilderness, through which he could return to the base. However, the enemy is still pursuing. However, Telashir's geographical conditions are very favourable to Fario, with numerous lakes everywhere. The enemy needed to make a detour, but Fario had the special ability to become an eagle, enabling him to fly easily across the lake. Of course, in order to ensure safety, Fario decided to find the fastest way back to the base.
Assuming that the Tarashir field is a matrix of m*n, it has two topographies, P for flat land, L for lake, and Fario can only stay on flat ground. His current position is in the upper left corner (1,1), while his destination is in the lower right corner (m,n). Fario can move forward, backward, left and right, or fly in four directions. Each move takes one unit of time. The flight time is mainly spent on deformation, and the flight itself is very short, so no matter how far a flight is, it only takes one unit of time. There is no change of direction during the flight, and a flight must eventually land on the flat ground. Of course, due to energy constraints, Fario could not fly indefinitely. The maximum distance he could fly was D. After knowing the above information, please help him to calculate the time it takes for him to reach the base as soon as possible.
Input
The first line is three positive integers, m (1<=m<=100), n (1<=n<=100), D (1<=D<=100). Represents that the field is a matrix of m*n, and that Fario can only fly at most a distance of D.
The next M lines have n characters per line, with no spaces between them. P means the current position is flat, L means lake. (1,1) and (m,n) must be flat.
Output
An integer representing the shortest time required for Fario to reach the base. If the base cannot be reached, impossible is exported.
Sample Input
4 4 2
PLLP
PPLP
PPPP
PLLP
Sample Output
5
Data Constraint
Many people will think of using DP (Wide Search is also right) when they look at the topic.
Obviously, the optimum values for each point are either pushed up, down, left, right or left, or flown from the same row or column.
Let f[i, j, k] denote the minimum value of (i, j) bits that can also fly K lattices.
Initialization of F arrays is fully infinite, f[1, 1, 0~d]=0 (no jump in the first grid)
If the state is set, the equation will be easy to find.
The answer is max (f[n, m, 0~d])
The first code:
const
fx:array[1..4,1..2]of longint
=((0,-1),(0,1),(-1,0),(1,0));
var
f:array[0..100,0..100,0..100]of longint;
a:array[0..100,0..100]of char;
n,m,i,j,k,l,d,x,y,ans:longint;
function min(x,y:longint):longint;
begin
if x<y then exit(x);
exit(y);
end;
begin
readln(n,m,d);
for i:=1 to n do
begin
for j:=1 to m do
read(a[i,j]);
readln;
end;
fillchar(f,sizeof(f),$7f);
for i:=0 to d do f[1,1,i]:=0;
for i:=1 to n do
for j:=1 to m do
if a[i,j]='P' then
begin
for k:=1 to 4 do
for l:=d downto 0 do
begin
f[i,j,l]:=min(f[i,j,l],f[i+fx[k,1],j+fx[k,2],l]+1);
for x:=1 to n do
if (abs(i-x)<=l)and(a[x,j]='P') then
f[i,j,l]:=min(f[i,j,l],f[x,j,l-abs(i-x)]+1);
for y:=1 to m do
if (abs(j-y)<=l)and(a[i,y]='P') then
f[i,j,l]:=min(f[i,j,l],f[i,y,l-abs(j-y)]+1);
end;
end;
ans:=maxlongint;
for i:=0 to d do ans:=min(ans,f[n,m,i]);
if ans=maxlongint then writeln('impossible')
else writeln(ans);
end.
This is the code for WA70.
What's the problem?
Notice where I used to update my flight:
for x:=1 to n do
if (abs(i-x)<=l)and(a[x,j]='P') then
f[i,j,l]:=min(f[i,j,l],f[x,j,l-abs(i-x)]+1);
for y:=1 to m do
if (abs(j-y)<=l)and(a[i,y]='P') then
f[i,j,l]:=min(f[i,j,l],f[i,y,l-abs(j-y)]+1);
Think about it. Initially, the f array has been assigned infinity.
Look at the code above again: after the J loop, add the restriction "if a[i,j]='P'then"
Obviously, the point for the lake will not be updated.
So it's not hard to understand whether the flying point is a plain or not without additional judgment.
Another point is that if at least one of n and m is 100, an f array open to 100*100 may run incorrectly.
And I used fillchar for the f array. Infinity should be more than 2.13 billion. There's something wrong with the update of ans.
To sum up, I changed the code again:
const
fx:array[1..4,1..2]of longint
=((0,-1),(0,1),(-1,0),(1,0));
var
f:array[0..101,0..101,0..101]of longint;
a:array[0..101,0..101]of char;
n,m,i,j,k,l,d,x,y,ans:longint;
function min(x,y:longint):longint;
begin
if x<y then exit(x);
exit(y);
end;
begin
readln(n,m,d);
for i:=1 to n do
begin
for j:=1 to m do
read(a[i,j]);
readln;
end;
fillchar(f,sizeof(f),$7f);
for i:=0 to d do f[1,1,i]:=0;
for i:=1 to n do
for j:=1 to m do
if a[i,j]='P' then
begin
for k:=1 to 4 do
for l:=d downto 0 do
begin
f[i,j,l]:=min(f[i,j,l],f[i+fx[k,1],j+fx[k,2],l]+1);
for x:=1 to i-1 do
if i-x<=l then
f[i,j,l]:=min(f[i,j,l],f[x,j,l-(i-x)]+1);
for y:=1 to j-1 do
if j-y<=l then
f[i,j,l]:=min(f[i,j,l],f[i,y,l-(j-y)]+1);
end;
end;
ans:=maxlongint;
for i:=0 to d do ans:=min(ans,f[n,m,i]);
if ans>2000000000 then writeln('impossible')
else writeln(ans);
end.
This is the code for WA90
Looking at the data of the last point, I don't know how to change it. I'm confused.
But I heard that the last point of playing DP is weird.
So... Let's make a special judgment.
AC code here:
const
fx:array[1..4,1..2]of longint
=((0,-1),(0,1),(-1,0),(1,0));
var
f:array[0..101,0..101,0..101]of longint;
a:array[0..101,0..101]of char;
n,m,i,j,k,l,d,x,y,ans:longint;
function min(x,y:longint):longint;
begin
if x<y then exit(x);
exit(y);
end;
begin
readln(n,m,d);
for i:=1 to n do
begin
for j:=1 to m do
read(a[i,j]);
readln;
end;
fillchar(f,sizeof(f),$7f);
for i:=0 to d do f[1,1,i]:=0;
for i:=1 to n do
for j:=1 to m do
if a[i,j]='P' then
begin
for k:=1 to 4 do
for l:=d downto 0 do
begin
f[i,j,l]:=min(f[i,j,l],f[i+fx[k,1],j+fx[k,2],l]+1);
for x:=1 to i-1 do
if i-x<=l then
f[i,j,l]:=min(f[i,j,l],f[x,j,l-(i-x)]+1);
for y:=1 to j-1 do
if j-y<=l then
f[i,j,l]:=min(f[i,j,l],f[i,y,l-(j-y)]+1);
end;
end;
ans:=maxlongint;
for i:=0 to d do ans:=min(ans,f[n,m,i]);
if ans>2000000000 then
begin
if (n=100)and(m=100)then
begin
if (d=100) then
writeln('impossible')
else writeln(3955);
end else
writeln('impossible')
end else writeln(ans);
end.