如何在国际象棋棋盘上为国王的最短路径做BFS?

时间:2014-01-13 17:33:27

标签: c++ algorithm breadth-first-search

我在标准的国际象棋坐标中给出了一个源索引和一个目标索引。现在我必须打印从源到目的地的最短路径。

#include <iostream>
#include <queue>
#include <string.h>
using namespace std;
int dx[]={1,1,1,-1,-1,-1,0,0};
int dy[]={1,0,-1,1,0,-1,1,-1};
int cost[10][10];
int parent[70];
bool visited[70];
int main()
{
    memset(parent,-1,sizeof parent);
    memset(visited,0,sizeof visited);
    memset(cost,255,sizeof cost);
    char a,b;
    cin>>a>>b;
    int s1 = a-'a',s2 = b-'0'-1;
    cin>>a>>b;
    int t1 = a-'a',t2 = b-'0'-1;
    queue<int> q;
    q.push(s1*8 + s2);
    visited[s1*8+s2] = true;
    cost[s1][s2] = 0;
    while(!q.empty())
     { 
        int u = q.front(),x=u/8,y=u%8;
        q.pop();
        for(int i=0;i<8;++i)
        {
            int vx = x+dx[i];
            int vy=y+dy[i];
            int v = vx*8+vy;
            if(vx<0 ||vy<0 || vx>=8 ||vy >=8)
                continue;
            visited[v] = true;
            parent[v] = u;
            q.push(v);

        }
    }
    int t = t1*8+t2;
    while(parent[t]!=(-1))
    {
        cout<<t/8<<" "<<t%8<<endl;
        t = parent[t];
   }
}

但是当我使用a8 h1之类的输入运行它时,路径不是最短的路径而是非常长的路径。我如何找到最短的路径?

3 个答案:

答案 0 :(得分:3)

你的BFS停止条款在哪里?

找到break后,您的主循环应x == t1 && y == t2
或者,您可以仅在parent[v]已经为真的情况下修改visited[v]
(如果您只想要最短的路径,第一个选项通常会更好。)

否则,您将继续开发更多路径,并覆盖到每个节点的最短路径。

答案 1 :(得分:2)

如果您访问某个节点,则不应多次更新受访阵列的单个条目,这意味着已找到最短路径(因为您的图表未加权)。此外,我没有看到您如何处理多个访问同一节点。看起来你忘了使用成本数组。

答案 2 :(得分:0)

Lee算法可能会有所帮助:https://en.wikipedia.org/wiki/Lee_algorithm。它是在矩阵中获取最短路径的bfs方式。