题目:
描述 Description
棋盘上A点有一个过河卒,需要走到目标B点。卒行走的规则:可以向下、或者向右。同时在棋盘上C点有一个对方的马,该马所在的点和所有跳跃一步可达的点称为对方马的控制点。因此称之为“马拦过河卒”。棋盘用坐标表示,A点(0, 0)、B点(n, m)(n, m为不超过15的整数),同样马的位置坐标是需要给出的。现在要求你计算出卒从A点能够到达B点的路径的条数,假设马的位置是固定不动的,并不是卒走一步马走一步。
输入格式 Input Format
一行四个数据,分别表示B点坐标和马的坐标。
输出格式 Output Format
一个数据,表示所有的路径条数。
分析
初看这道题的第一反应,就是搜索。但实际上,不一定要用搜索。我们可以先画一个图,打草稿。
那么现在也就一目了然了。写进代码中,就是下文中的效果。
代码:
var
dx:array[1..8] of integer=(-2,-1,1,2,2,1,-1,-2); //马在x轴上的控制点
dy:array[1..8] of integer=(1,2,2,1,-1,-2,-2,-1); //马在y轴上的控制点
n,m,x,y,i,j:integer;
g:array[0..20,0..20] of integer; //表示当前坐标可不可以走
f:array[0..20,0..20] of int64; //至该店的路径条数
begin
readln(n,m,x,y); //读入B点和马的坐标
g[x,y]:=1; //赋初值(不可走)
for i:=1 to 8 do
if(x+dx[i]>=0)and(x+dx[i]<=n)and(y+dy[i]>=0)and(y+dy[i]<=m)then //循环控制点(不超过边界)
g[x+dx[i],y+dy[i]]:=1; //设置标记(不可走)
f[0,0]:=1; //起点(1条)
for i:=1 to n do
if g[i,0]=0 then f[i,0]:=f[i-1,0]; //设置左边界
for j:=1 to m do
if g[0,j]=0 then f[0,j]:=f[0,j-1]; //设置上边界
for i:=1 to n do
for j:=1 to m do //双循环查找
if g[i,j]=0 then //要可走的
f[i,j]:=f[i-1,j]+f[i,j-1]; //算出路径条数
writeln(f[n,m]); //输出路径总数
end.