HDU1043 八数码(BFS + 打表)
题目链接:http://acm.hdu.edu.cn/showproblem.php?pid=1043 , 康托展开 + BFS + 打表。
经典八数码问题,传说此题不做人生不完整,关于八数码的八境界:http://www.cnblogs.com/goodness/archive/2010/05/04/1727141.html
我自己是用哈希(康托展开) + BFS + 打表过的,第三重境界。
由于一些高级的搜索现在还没学,所以目前能升级的也就是用双向BFS来做了,等过几天有心情了来做。
本文长期更新。
算法:
由于此题是求某个起始状态到“12345678X”的步骤,所以可以考虑先求出“12345678X”的所有变换的步骤,即打表预处理。
这里要注意就是最后输出的时候,由于我们求得是逆序,所以要倒序输出,倒序输出的时候要注意'u'、'd'、'l'、'r'都应该颠倒过来,比如说你从A状态向上变换为B状态,这时你从B变为A就要向下变换。
这里哈希还是用的康托展开,这个问题我在上一篇博客中有提到过。
BFS + 打表:
#include <iostream>
#include <cstdio>
#include <vector>
#include <queue>
#include <cmath>
#include <string>
#include <string.h>
#include <algorithm>
using namespace std;
#define LL __int64
#define eps 1e-8
#define INF 1e8
#define lson l , m , rt << 1
#define rson m + 1 , r , rt << 1 | 1
const int MOD = ;
const int maxn = ;
bool vis[maxn];
string ans[maxn];
int fac[]={ , , , , , , , , , }; int Cantor(string str)
{
int ret = ;
int n = str.size();
for(int i = ; i < n ; i++) {
int cnt = ;
for(int j = i ; j < n ; j++)
if(str[j] < str[i])
cnt++;
ret += cnt * fac[n - i - ];
}
return ret;
}
void move_Up(string &str , int pos)
{
swap(str[pos] , str[pos - ]);
}
void move_Down(string &str , int pos)
{
swap(str[pos] , str[pos + ]);
}
void move_Left(string &str , int pos)
{
swap(str[pos] , str[pos - ]);
}
void move_Right(string &str , int pos)
{
swap(str[pos] , str[pos + ]);
}
void BFS(string start)
{
memset(vis , , sizeof(vis));
queue <string> que;
que.push(start);
int x = Cantor(start);
vis[x] = ;
ans[x] = "";
int pos;
while(!que.empty()) {
string u = que.front();
que.pop();
int i = Cantor(u);
for(pos = ; pos < ; pos++)
if(u[pos] == 'x')
break; if(pos > ) {
string tmp = u;
move_Up(tmp , pos);
int k = Cantor(tmp);
if(!vis[k]) {
vis[k] = ;
que.push(tmp);
ans[k] = ans[i] + 'u';
}
}
if(pos < ) {
string tmp = u;
move_Down(tmp , pos);
int k = Cantor(tmp);
if(!vis[k]) {
vis[k] = ;
que.push(tmp);
ans[k] = ans[i] + 'd';
}
}
if(pos % != ) {
string tmp = u;
move_Left(tmp , pos);
int k = Cantor(tmp);
if(!vis[k]) {
vis[k] = ;
que.push(tmp);
ans[k] = ans[i] + 'l';
}
}
if(pos % != ) {
string tmp = u;
move_Right(tmp , pos);
int k = Cantor(tmp);
if(!vis[k]) {
vis[k] = ;
que.push(tmp);
ans[k] = ans[i] + 'r';
}
}
}
}
int main()
{
char ch[];
string start = "12345678x";
BFS(start);
while(gets(ch))
{
string str = "";
for(int i = ; ch[i] != '\0' ; i++) {
if(ch[i] == ' ')
continue;
else
str += ch[i];
}
int k = Cantor(str);
if(vis[k]) {
for(int i = ans[k].size() - ; i >= ; i--) {
if(ans[k][i] == 'u')
putchar('d');
else if(ans[k][i] == 'd')
putchar('u');
else if(ans[k][i] == 'l')
putchar('r');
else
putchar('l');
}
puts("");
} else {
cout << "unsolvable" << endl;
}
}
return ;
}
HDU1043 八数码(BFS + 打表)的更多相关文章
- hdu-1043(八数码+bfs打表+康托展开)
参考文章:https://www.cnblogs.com/Inkblots/p/4846948.html 康托展开:https://blog.csdn.net/wbin233/article/deta ...
- 紫书p199 八数码(BFS,hash)
八数码问题 紫书上的简单搜索 渣渣好久才弄懂 #include<cstdio> #include<cstring> using namespace std; const i ...
- code1225 八数码Bfs
Bfs搜索 1.把棋盘直接作为状态: #include<iostream> #include<cstring> #include<queue> #include&l ...
- POJ1077 八数码 BFS
BFS 几天的超时... A*算法不会,哪天再看去了. /* 倒搜超时, 改成顺序搜超时 然后把记录路径改成只记录当前点的操作,把上次的位置记录下AC..不完整的人生啊 */ #include < ...
- POJ1077&&HDU1043(八数码,IDA*+曼哈顿距离)
Eight Time Limit: 1000MS Memory Limit: 65536K Total Submissions: 30127 Accepted: 13108 Special ...
- luogu_1379 八数码难题
八数码-->BFS+set #include<iostream> #include<cstdlib> #include<cstdio> #include< ...
- HDU-1043 Eight八数码 搜索问题(bfs+hash 打表 IDA* 等)
题目链接 https://vjudge.net/problem/HDU-1043 经典的八数码问题,学过算法的老哥都会拿它练搜索 题意: 给出每行一组的数据,每组数据代表3*3的八数码表,要求程序复原 ...
- hdu1043 经典的八数码问题 逆向bfs打表 + 逆序数
题意: 题意就是八数码,给了一个3 * 3 的矩阵,上面有八个数字,有一个位置是空的,每次空的位置可以和他相邻的数字换位置,给你一些起始状态 ,给了一个最终状态,让你输出怎么变换才能达到目的. 思路: ...
- poj 1077-Eight(八数码+逆向bfs打表)
The 15-puzzle has been around for over 100 years; even if you don't know it by that name, you've see ...
随机推荐
- datagrid 绑定选中数据,列头全选
成品图: xaml代码 <Grid> <DataGrid x:Name="datagrid" Height="Auto" Width=&quo ...
- bat实现监测计算机无线连接,断网自动重启无线
@echo off :Begin ping www.baidu.com if errorlevel 1 goto Reboot if errorlevel 0 goto Continue :Conti ...
- BKMyFAQ
邮箱配置如图 发送格式: { "bk_app_code": "bk_monitor", #该字段可以查看文件:/data/install/.app.token ...
- 在 windows 下搭建 IDEA + Spark 连接 Hive 的环境
为了开发测试方便,想直接在 IDEA 里运行 Spark 程序,可以连接 Hive,需不是打好包后,放到集群上去运行.主要配置工作如下: 1. 把集群环境中的 hive-core.xml, hdfs- ...
- elasticsearch 聚合查询
1. 按照 tags 字段 进行分组 GET /ecommerce/product/_search{ "size": 0, "aggs": { &quo ...
- 洛谷P3478 [POI2008]STA-Station
P3478 [POI2008]STA-Station 题目描述 The first stage of train system reform (that has been described in t ...
- 使用pods添加第三方的时候,出现ld: library not found for -lpop
ld: library not found for -lpop 错误,是在使用pods添加第三方的时候,出现的编译错误,同时伴随着的是error: linker command failed with ...
- web综合案例01
web综合案例01 ... .... 内容待添加
- day14内置函数作业详解
day14题目 day14作业及默写 1,整理今天所学内容,整理知识点,整理博客. 2,画好流程图. 3,都完成的做一下作业(下面题都是用内置函数或者和匿名函数结合做出): 4,用map来处理字符串列 ...
- Angular学习笔记之组件之间的交互
1.@Input:可设置属性 当它通过属性绑定的形式被绑定时,值会“流入”这个属性. 在子组件中使用,例如:@Input()name:string 父组件定义宾亮,并在父组件的模板中绑定,例如: 子组 ...