小米 oj 马走日 (bfs 或 双向bfs)

小米 oj 马走日 (bfs 或 双向bfs) 马走日

序号:#56难度:困难时间限制:1500ms内存限制:10M

描述

在中国象棋中,马只能走日字型。现在给出一个由 N*M 个格子组成的中国象棋棋盘( 有(N+1)*(M+1)个交叉点可以落子 ),以及棋盘上的两个坐标点 S,T。请计算出从 S 到 T 使用日字型走法所需的最少步数,如果不能到达,则输出-1。

下图为一个 1x2 的棋盘,起始落子点(蓝色)为 (0, 0),目标落子点(绿色)为 (1,2) 的示意,此时需要的步数为 1

小米 oj 马走日 (bfs 或 双向bfs)

输入

每行输入6个数,由;分隔,第一个数N,第二个数是M,接下来两个数是 S 点的 x,y 坐标,接着是 T 点的 x,y 坐标。输入保证满足 (1<=N<=1000, 1<=M<=1000, 0<=x<=N, 0<=y<=M)

输出

所需的最少步数,不能到达则输出-1

输入样例

1;1;0;0;1;1
1;2;0;0;1;2
2;2;0;0;2;0

 复制样例

输出样例

-1
1
2

一般bfs:

#include<bits/stdc++.h>
using namespace std;
typedef long long ll;
int n,m;
int sx,sy,des_x,des_y;
string buf;
int dx[8]={1,1,-1,-1,2,2,-2,-2};
int dy[8]={2,-2,2,-2,1,-1,1,-1};
bool vis[1005][1005];
int x[1005*1005];
int y[1005*1005];
int depth[1005][1005];
int que[1005*1005];
int ans;
int bfs()
{
    memset(vis,0,sizeof(vis));
    int front=0;int tail=0;
    x[tail]=sx;y[tail++]=sy;depth[sx][sy]=1;vis[sx][sy]=1;
    int now_x,now_y,nxt_x,nxt_y;
    while(front<=tail)
    {
        now_x=x[front];now_y=y[front++];
        if(now_x==des_x&&now_y==des_y)
        {
            return depth[now_x][now_y]-1;
        }
        for(int i=0;i<8;i++)
        {
            nxt_x=now_x+dx[i];nxt_y=now_y+dy[i];
            if(!vis[nxt_x][nxt_y]&&nxt_x>=0&&nxt_x<=n&&nxt_y>=0&&nxt_y<=m)
            {
                vis[nxt_x][nxt_y]=1;
                x[tail]=nxt_x;y[tail++]=nxt_y;
                depth[nxt_x][nxt_y]=depth[now_x][now_y]+1;
            }
        }
    }
    return -1;
}
int main()
{
  //  freopen("in.txt","r",stdin);
    while(cin>>buf)
    {
        for(int i=0;i<buf.size();i++)
        {
            if(buf[i]==';')buf[i]=' ';
        }
        stringstream ss(buf);
        ss>>n>>m>>sx>>sy>>des_x>>des_y;
        ans=bfs();
        printf("%d
",ans);
    }
    return 0;
}

双向bfs:

#include<iostream>
#include<string.h>
#include<stdio.h>
#include<algorithm>
#include<sstream>
using namespace std;
typedef long long ll;
int n,m;
int sx,sy,des_x,des_y;
string buf;
int dx[8]={1,1,-1,-1,2,2,-2,-2};
int dy[8]={2,-2,2,-2,1,-1,1,-1};
bool vis1[1005][1005];
int x_1[1005*1005];
int y_1[1005*1005];
int d1[1005][1005];
bool vis2[1005][1005];
int x_2[1005*1005];
int y_2[1005*1005];
int d2[1005][1005];
int ans;
int bfs()
{
    memset(vis1,0,sizeof(vis1));memset(vis2,0,sizeof(vis2));
    int f1=0;int t1=0;int f2=0;int t2=0;
    d1[sx][sy]=0;d2[des_x][des_y]=0;
    x_1[t1]=sx;y_1[t1++]=sy;x_2[t2]=des_x;y_2[t2++]=des_y;
    vis1[sx][sy]=1;vis2[des_x][des_y]=1;
    int now_x_1,now_y_1,now_x_2,now_y_2;
    int nxt_x,nxt_y;
    while(f1<=t1||f2<=t2)
    {
        now_x_1=x_1[f1];now_y_1=y_1[f1++];now_x_2=x_2[f2];now_y_2=y_2[f2++];
        if(f1<=t1&&vis1[now_x_2][now_y_2])
        {
            return d1[now_x_2][now_y_2]+d2[now_x_2][now_y_2];
        }
        if(f2<=t2&&vis2[now_x_1][now_y_1])
        {
            return d2[now_x_1][now_y_1]+d1[now_x_1][now_y_1];
        }
        for(int i=0;i<8;i++)
        {
            nxt_x=now_x_1+dx[i];nxt_y=now_y_1+dy[i];
            if(!vis1[nxt_x][nxt_y]&&nxt_x>=0&&nxt_x<=n&&nxt_y>=0&&nxt_y<=m)
            {
                vis1[nxt_x][nxt_y]=1;
                d1[nxt_x][nxt_y]=d1[now_x_1][now_y_1]+1;
                x_1[t1]=nxt_x;y_1[t1++]=nxt_y;
            }
        }
        for(int i=0;i<8;i++)
        {
            nxt_x=now_x_2+dx[i];nxt_y=now_y_2+dy[i];
            if(!vis2[nxt_x][nxt_y]&&nxt_x>=0&&nxt_x<=n&&nxt_y>=0&&nxt_y<=m)
            {
                vis2[nxt_x][nxt_y]=1;
                d2[nxt_x][nxt_y]=d2[now_x_2][now_y_2]+1;
                x_2[t2]=nxt_x;y_2[t2++]=nxt_y;
            }
        }
    }
    return -1;
}
int main()
{
    //freopen("in.txt","r",stdin);
    while(cin>>buf)
    {
        for(int i=0;i<buf.size();i++)
        {
            if(buf[i]==';')buf[i]=' ';
        }
        stringstream ss(buf);
        ss>>n>>m>>sx>>sy>>des_x>>des_y;
        ans=bfs();
        printf("%d
",ans);
    }
    return 0;
}