首页 > 代码库 > poj-1915- Knight Moves

poj-1915- Knight Moves

题目大意:给一个边长为len的棋盘,然后给出起点和终点的坐标,求马从起点到终点最少需要走几步!


题解:这个题的题意是很好理解的,要求我们求最少需要走的步数,我们在这可以想到用bfs来解决这个问题,由于在这个棋盘中,马棋有八种路可以选择进行跳跃,所以开辟两个方向数组xx[]和yy[],然后再进行相应操作即可!


这道题我写了四次,用了不同的方法,区别其实也不大,只是写法的问题!这个题其实只要是选择使用了bfs的话,没什么细节问题的话,都是能AC的,不过用时有些不同!

第一种是最快的,是用的数组写的队列!


下面是我写的四份代码:

#include<stdio.h>
#include<string.h>
int t,len,sx,sy,lx,ly;
int vis[315][315];
int xx[8]= {1,1,-2,-2,2,2,-1,-1};
int yy[8]= {-2,2,1,-1,1,-1,2,-2};
struct Node
{
    int x,y,step;
}knight[201314];
int knight_moves(int n)
{
    Node dangqi;
    Node change;
    int first=0,last=1;
    //头.尾!
    knight[0].x=sx;
    knight[0].y=sy;
    knight[0].step=0;
    memset(vis,0,sizeof(vis));
    while(last>first)
    {
        dangqi=knight[first++];//此处为出队!
        if(dangqi.x==lx&&dangqi.y==ly)
        return dangqi.step;
        else
        {
            for(int i=0;i<8;i++)
            {
                int X=dangqi.x+xx[i];
                int Y=dangqi.y+yy[i];
                if(X>=0&&X<n&&Y>=0&&Y<n&&vis[X][Y]==0)
                {
                    vis[X][Y]=1;
                    change.x=X;
                    change.y=Y;
                    change.step=dangqi.step+1;//棋子移动一次,步数step就加一次!
                    knight[last++]=change;//入队!
                }
            }
        }
    }
}
int main()
{
    scanf("%d",&t);
    while(t--)
    {
        scanf("%d",&len);
        scanf("%d%d",&sx,&sy);
        scanf("%d%d",&lx,&ly);
        int ans=knight_moves(len);
        printf("%d\n",ans);
    }
    return 0;
}

第二种:用的STL模板写的!

#include<cstdio>
#include<cstring>
#include<queue>
#include<iostream>
using namespace std;
int len,sx,dx,sy,dy;
bool vis[315][315];
int xx[8]={1,1,-2,-2,2,2,-1,-1};
int yy[8]={-2,2,1,-1,1,-1,2,-2};
struct horse
{
    int x,y,step;
}now;
void knight_moves(int n)
{
    queue<horse>Q;
    memset(vis,false,sizeof(vis));
    now.x=sx,now.y=sy,now.step=0;
    Q.push(now);
    while(!Q.empty())
    {
        horse u=Q.front();
        Q.pop();
        if(u.x==dx&&u.y==dy)
        {
            cout<<u.step<<endl;
            return ;
        }
        for(int i=0;i<8;i++)
        {
            int X=xx[i]+u.x;
            int Y=yy[i]+u.y;
            if(!vis[X][Y]&&X>=0&&X<n&&Y>=0&&Y<n)
            {
                vis[X][Y]=true;
                horse v;
                v.x=X,v.y=Y,v.step=u.step+1;
                Q.push(v);

            }
        }
    }
}
int main()
{
    int T;
    cin>>T;
    while(T--)
    {
        cin>>len>>sx>>sy>>dx>>dy;
        knight_moves(len);
    }
    return 0;
}

第三种:

#include<cstdio>
#include<cstring>
#include<queue>
#include<iostream>
using namespace std;
int len,sx,dx,sy,dy;
bool vis[315][315];
int step[315][315];
int xx[8]={1,1,-2,-2,2,2,-1,-1};
int yy[8]={-2,2,1,-1,1,-1,2,-2};
void knight_moves(int n)
{
    queue<int>Q;
    memset(vis,false,sizeof(vis));
    memset(step,0,sizeof(step));
    Q.push(sx);
    Q.push(sy);
    while(!Q.empty())
    {
        int x=Q.front();
        Q.pop();
        int y=Q.front();
        Q.pop();
        if(x==dx&&y==dy)
        {
            printf("%d\n",step[x][y]);
            return ;
        }
        for(int i=0;i<8;i++)
        {
            int X=xx[i]+x;
            int Y=yy[i]+y;
            if(!vis[X][Y]&&X>=0&&X<n&&Y>=0&&Y<n)
            {
                vis[X][Y]=true;
                step[X][Y]=step[x][y]+1;
                Q.push(X);
                Q.push(Y);

            }
        }
    }
}
int main()
{
    int T;
    scanf("%d",&T);
    while(T--)
    {
        scanf("%d",&len);
        scanf("%d%d",&sx,&sy);
        scanf("%d%d",&dx,&dy);
        knight_moves(len);
    }
    return 0;
}

第四种:

#include<cstdio>
#include<cstring>
#include<queue>
#include<iostream>
using namespace std;
int len,sx,dx,sy,dy;
bool vis[315][315];
int step[315][315];
int xx[8]={1,1,-2,-2,2,2,-1,-1};
int yy[8]={-2,2,1,-1,1,-1,2,-2};
void knight_moves(int n)
{
    queue<int>Qx;
    queue<int>Qy;
    memset(vis,false,sizeof(vis));
    memset(step,0,sizeof(step));
    Qx.push(sx);
    Qy.push(sy);
    while(!Qx.empty())
    {
        int x=Qx.front();
        Qx.pop();
        int y=Qy.front();
        Qy.pop();
        //vis[x][y]=false;
        if(x==dx&&y==dy)
        {
            printf("%d\n",step[x][y]);
            return ;
        }
        for(int i=0;i<8;i++)
        {
            int X=xx[i]+x;
            int Y=yy[i]+y;
            if(!vis[X][Y]&&X>=0&&X<n&&Y>=0&&Y<n)
            {
                vis[X][Y]=true;
                step[X][Y]=step[x][y]+1;
                Qx.push(X);
                Qy.push(Y);

            }
        }
    }
}
int main()
{
    int T;
    scanf("%d",&T);
    while(T--)
    {
        scanf("%d",&len);
        scanf("%d%d",&sx,&sy);
        scanf("%d%d",&dx,&dy);
        knight_moves(len);
    }
    return 0;
}


poj-1915- Knight Moves