BFS解决八数码问题

八数码问题

原题链接:https://www.acwing.com/problem/content/847/

  • 数据的表示和存储

    1. 首先是八数码的存储方式:此题选择用字符串来存,每一个状态使用一个字符串来存储
    2. 使用队列queue来存储各种状态
    3. 记录每个状态和初始状态的距离:unordered_map<string,int>来存储
  • bfs函数

    1. 初始状态进入队列
    2. while(q.size())
    3. 弹出队列首元素
    4. 如果首元素就是答案,则返回其对应到初始状态的距离
    5. 在该字符串找到'x'
    6. 字符串中的下标转换为图中的坐标
    7. 上下左右四个方向循环
    8. 如果上下左右不出界并且该状态未访问过,则加入到队列中
    9. 记得在下一次循环前返回到原状态!
    10. 如果队列空了,仍未与end相同,则返回-1
#include <bits/stdc++.h>

using namespace std;


int bfs(string start)
{
    string end = "12345678x";
    unordered_map<string,int> d;
    queue<string> q;
    q.push(start);
    d[start] = 0;
    int xx[4] = {-1,0,1,0};
    int yy[4] = {0,1,0,-1};
    while(q.size())
    {
        string t = q.front();
        q.pop();
        if(t == end)
            return d[t];
        int k = t.find('x');
        int x = k / 3;
        int y = k % 3;
        int dis = d[t];
        for(int i = 0; i < 4; i++)
        {
            int a = x + xx[i];
            int b  = y + yy[i];
            if(a >= 0 && a < 3 && b >= 0 && b < 3)
            {
                swap(t[k],t[a*3+b]);
                if(!d.count(t))
                {
                    d[t] = dis + 1;
                    q.push(t);
                }
                swap(t[k],t[a*3+b]);
            }
        }
    }
  
    return -1;
}

int main()
{
    string start;
    char c[2];
    for(int i = 0; i < 9; i++)
    {
        cin >> c;
        start += *c;
    }
    cout << bfs(start) << endl;
}
posted @ 2022-08-12 19:05  火车驶向云外0218  阅读(66)  评论(0)    收藏  举报