c++ 廣度優先搜尋(寬搜)

牛大了的牛大發表於2019-07-14

c++ bfs基本應用

Knight Moves

題目描述

貝茜和她的表妹在玩一個簡化版的國際象棋。棋盤如圖所示:
c++ 廣度優先搜尋(寬搜)
貝茜和表妹各有一顆棋子。棋子每次移一步,且棋子只能往如圖所示的八個方向移動。比賽的規則很簡單,兩個人需要從起點將棋子移到終點,誰能花最少的步數從起點走到終點,就是贏家。
為了確保能贏表妹,貝茜希望每次都能算出最少的步數,你能幫助她麼?

輸入

輸入起點和終點,用一個空格隔開。(確保起點一定能走到終點)

輸出

輸入最少的步數。

樣例輸入

a1 b2

樣例輸出

4

上程式碼:

AC程式碼

#include <bits/stdc++.h>
using namespace std;
struct Point
{
    int x,y,step;
};
Point q[1000000],s,t;//t是終點,s是起點 
int dx[8]={1,-1,1,-1,2,2,-2,-2};//dx[] + dy[] 代表Knight走的8個方向可達的點 
int dy[8]={2,2,-2,-2,1,-1,1,-1};
int f=1,e=0;
int main()
{
    char ca,cb,cc,cd;
    scanf("%c%c %c%c",&ca,&cb,&cc,&cd);//輸入 
    s.x=ca-'a'+1,s.y=cb-'1'+1;s.step=0;//把a轉換成數字1 把字元1轉換成數字1 
    t.x=cc-'a'+1,t.y=cd-'1'+1;t.step = 0;//把b轉換成數字2 把字元2轉換成數字2 
    if(s.x==t.x&&s.y==t.y)//如果起點等於終點,就直接退出 
    {
        printf("0\n");
        return 0;
    }
    e++;//佇列入隊時候的下標
     
    q[e]=s;//q就是佇列 把所有待查詢的元素放在q佇列裡面 
    while(f<=e)//出隊的下標不能大於入隊時候的下標 
    {
        Point u=q[f];//f是佇列出隊時候的下標      //* u是在佇列中選定的騎士 *//
        for(int i=0;i<8;i++)//for迴圈為了能 加上dx[] 和dy[] 
        {
            Point v;//v是有效的騎士 
            v.x = u.x + dx[i],v.y = u.y + dy[i],v.step=u.step + 1;//把選定的位置向8個方向擴充套件(一次) 
            if(v.x<1||v.x>8||v.y<1||v.y>8)continue;//如果這個騎士的位置不在棋盤上,則丟棄 
            if(t.x==v.x&&t.y==v.y)//找到了終點 
            {
                printf("%d\n",v.step);//輸出步數 
                return 0;
            }
            e++;// 把入隊下標 + 1 
            q[e]=v;//  入隊 
        }
        f++;//出隊下標 + 1 
    }
    return 0;
}

相關文章