Eight hdu 1043 poj 1077
Description
The 15-puzzle has been around for over 100 years; even if you don't know it by that name, you've seen it. It is constructed with 15 sliding tiles, each with a number from 1 to 15 on it, and all packed into a 4 by 4 frame with one tile missing. Let's call the missing tile 'x'; the object of the puzzle is to arrange the tiles so that they are ordered as:
- 1 2 3 4
5 6 7 8
9 10 11 12
13 14 15 x
where the only legal operation is to exchange 'x' with one of the tiles with which it shares an edge. As an example, the following sequence of moves solves a slightly scrambled puzzle:
- 1 2 3 4 1 2 3 4 1 2 3 4 1 2 3 4
5 6 7 8 5 6 7 8 5 6 7 8 5 6 7 8
9 x 10 12 9 10 x 12 9 10 11 12 9 10 11 12
13 14 11 15 13 14 11 15 13 14 x 15 13 14 15 x
r-> d-> r->
The letters in the previous row indicate which neighbor of the 'x' tile is swapped with the 'x' tile at each step; legal values are 'r','l','u' and 'd', for right, left, up, and down, respectively.
Not all puzzles can be solved; in 1870, a man named Sam Loyd was famous for distributing an unsolvable version of the puzzle, and
frustrating many people. In fact, all you have to do to make a regular puzzle into an unsolvable one is to swap two tiles (not counting the missing 'x' tile, of course).
In this problem, you will write a program for solving the less well-known 8-puzzle, composed of tiles on a three by three
arrangement.
Input
You will receive, several descriptions of configuration of the 8 puzzle. One description is just a list of the tiles in their initial positions, with the rows listed from top to bottom, and the tiles listed from left to right within a row, where the tiles are represented by numbers 1 to 8, plus 'x'. For example, this puzzle
1 2 3
x 4 6
7 5 8
is described by this list:
1 2 3 x 4 6 7 5 8
Output
You will print to standard output either the word ``unsolvable'', if the puzzle has no solution, or a string consisting entirely of the letters 'r', 'l', 'u' and 'd' that describes a series of moves that produce a solution. The string should include no spaces and start at the beginning of the line. Do not print a blank line between cases.
Sample Input
Sample Input
- #include <iostream>
- #include <cstring>
- using namespace std;
- const int maxn = ;
- typedef int State[];
- State st[maxn];
- int goal[] = {, , , , , , , , };
- int dx[] = {-, , , };
- int dy[] = { , , -, };
- int head[maxn], nxt[maxn], fa[maxn];
- char dir[maxn];
- int Hash(State s) //哈希函数
- {
- int ret = , i;
- for(i = ; i < ; i++) ret = ret * + s[i];
- return ret % maxn;
- }
- bool try_to_insert(int rear) //插入哈希表
- {
- int h = Hash(st[rear]);
- for(int e = head[h]; e != -; e = nxt[e])
- {
- if(memcmp(st[e], st[rear], sizeof(st[e])) == ) return ;
- }
- nxt[rear] = head[h];
- head[h] = rear;
- return ;
- }
- int bfs() //遍历
- {
- int frt = , rear = , i, z;
- while(frt < rear)
- {
- State& s = st[frt];
- if(memcmp(s, goal, sizeof(s)) == ) return frt;
- for(z = ; s[z] != ; z++);
- int x = z / ;
- int y = z % ;
- for(i = ; i < ; i++)
- {
- int newx = x + dx[i];
- int newy = y + dy[i];
- int newz = * newx + newy;
- if(newx >= && newx < && newy >= && newy < )
- {
- State& news = st[rear];
- memcpy(news, s, sizeof(s));
- news[z] = s[newz];
- news[newz] = ;
- if(try_to_insert(rear)) //注意这里的路径输出的方式
- {
- fa[rear] = frt;
- switch(i)
- {
- case : dir[rear] = 'u'; break;
- case : dir[rear] = 'd'; break;
- case : dir[rear] = 'l'; break;
- case : dir[rear] = 'r'; break;
- default: break;
- }
- rear++;
- }
- }
- }
- frt++;
- }
- return ;
- }
- void print(int i) //输出
- {
- if(fa[i] == -) return;
- print(fa[i]);
- cout<<dir[i];
- }
- int main()
- {
- char c[];
- int i, ret;
- while(cin>>c[]>>c[]>>c[]>>c[]>>c[]>>c[]>>c[]>>c[]>>c[])
- {
- for(i = ; i < ; i++) st[][i] = c[i] == 'x' ? : (int)(c[i]-'');
- memset(head, -, sizeof(head));
- fa[] = -;
- ret = bfs();
- if(ret)
- {
- print(ret);
- }
- else cout<<"unsolvable";
- cout<<endl;
- }
- return ;
- }
HDU : 这道题时多组输入,所以不能向上面一样在线写,而是要从最终状态开始倒着把所有状态搜索一遍,之后只需要输入初始状态打表判断输出路径即可;
学习到的知识有两个:bfs()路径查找类 + 康拓展开,路径的输出:
- /*************************************************************************
- > File Name: search.cpp
- > Author : PrayG
- > Mail: 996930051@qq,com
- > Created Time: 2016年07月20日 星期三 10时56分09秒
- ************************************************************************/
- #include<iostream>
- #include<cstdio>
- #include<cstring>
- #include<string>
- #include<queue>
- #include<algorithm>
- #include<map>
- #include<stack>
- #include<set>
- #include<cmath>
- using namespace std;
- const int maxn = ;
- int fac[] = {,,,,,,,,,};
- int dx[] = {,,-,},dy[] = {,,,-};//drul
- char ind[] = "uldr";//与上面相反
- string path[maxn];//记录路径
- bool vis[maxn];
- int aim = ;//123456780 的康拓展开
- struct node
- {
- int s[]; //记录状态
- int sit0; //0 的位置
- int val; //康拓展开的值
- string path; // 路径
- };
- int cant(int s[]) //康拓展开
- {
- int code = ;
- for(int i = ; i < ; i++)
- {
- int cnt = ;
- for(int j= i+ ; j < ; j++)
- {
- if(s[i] > s[j])
- {
- cnt++;
- }
- }
- code += fac[-i] * cnt;
- }
- return code;
- }
- void bfs()
- {
- memset(vis,false,sizeof(vis));
- queue<node> que;
- node cnt1,cnt2;
- for(int i = ; i < ;i++)
- cnt1.s[i] = i+;
- cnt1.s[] = ;
- cnt1.sit0 = ;
- //printf("aim = %d\n",aim);
- cnt1.val = aim;
- cnt1.path = "";
- path[aim] = "";
- que.push(cnt1);
- while(!que.empty())
- {
- cnt1 = que.front();
- que.pop();
- int x = cnt1.sit0 / ;
- int y = cnt1.sit0 % ;
- for(int i = ; i < ; i++)
- {
- int nx = x + dx[i];
- int ny = y + dy[i];
- int nz = nx * + ny;
- if(nx < || nx > || ny < || ny >)
- continue;
- cnt2 = cnt1;
- cnt2.s[cnt1.sit0] = cnt2.s[nz];
- cnt2.s[nz] = ;
- cnt2.sit0 = nz;
- cnt2.val = cant(cnt2.s);
- if(!vis[cnt2.val])
- {
- vis[cnt2.val] = true;
- cnt2.path = ind[i] + cnt1.path;
- que.push(cnt2);
- path[cnt2.val] = cnt2.path;
- }
- }
- }
- }
- int main()
- {
- bfs();
- char t;
- while(cin >> t)
- {
- node st;
- if(t == 'x'){
- st.s[] = ;
- st.sit0 = ;
- }
- else
- st.s[] = t - '';
- for(int i = ; i< ; i++)
- {
- cin >> t;
- if(t == 'x')
- {
- st.s[i] = ;
- st.sit0 = i;
- }
- else
- st.s[i] = t -'';
- }
- st.val = cant(st.s);
- if(vis[st.val])
- {
- cout << path[st.val] << endl;
- }
- else
- cout << "unsolvable" << endl;
- }
- return ;
- }
Eight hdu 1043 poj 1077的更多相关文章
- HDU 1043 & POJ 1077 Eight(康托展开+BFS+预处理)
Eight Time Limit: 1000MS Memory Limit: 65536K Total Submissions: 30176 Accepted: 13119 Special ...
- HDU 1043 & POJ 1077 Eight(康托展开+BFS | IDA*)
Eight Time Limit: 1000MS Memory Limit: 65536K Total Submissions: 30176 Accepted: 13119 Special ...
- Eight (HDU - 1043|POJ - 1077)(A* | 双向bfs+康拓展开)
The 15-puzzle has been around for over 100 years; even if you don't know it by that name, you've see ...
- Eight POJ - 1077 HDU - 1043 八数码
Eight POJ - 1077 HDU - 1043 八数码问题.用hash(康托展开)判重 bfs(TLE) #include<cstdio> #include<iostream ...
- HDU - 1043 - Eight / POJ - 1077 - Eight
先上题目: Eight Time Limit: 10000/5000 MS (Java/Others) Memory Limit: 65536/32768 K (Java/Others)Tota ...
- HDU 1403 Eight&POJ 1077(康拖,A* ,BFS,双广)
Eight Time Limit: 10000/5000 MS (Java/Others) Memory Limit: 65536/32768 K (Java/Others) Total Submis ...
- HDU 3695 / POJ 3987 Computer Virus on Planet Pandora(AC自动机)(2010 Asia Fuzhou Regional Contest)
Description Aliens on planet Pandora also write computer programs like us. Their programs only consi ...
- hdu 2844 poj 1742 Coins
hdu 2844 poj 1742 Coins 题目相同,但是时限不同,原本上面的多重背包我初始化为0,f[0] = 1;用位或进行优化,f[i]=1表示可以兑成i,0表示不能. 在poj上运行时间正 ...
- HDU 1043 八数码(八境界)
看了这篇博客的讲解,挺不错的.http://www.cnblogs.com/goodness/archive/2010/05/04/1727141.html 判断无解的情况(写完七种境界才发现有直接判 ...
随机推荐
- * ? 【a-z】【0-9】通配符 学习
通配符顾名思义就是通用的匹配信息的符号,比如星号(*)就是代表匹配零个或多个字符,问号(?)是代表匹配单个字符,中括号内加上数字[0-9]代表匹配单个阿拉伯数字的字符,而中括号内加上字母[abc]则是 ...
- ztree实现根节点单击事件,显示节点信息
这段时间在维护公司的项目,去年做的项目里面有ztree树的例子,想起之前还没有开始写博客,一些知识点也无从找起,要新加一个右击节点事件,折腾了半天,其中也包含了一些知识点,稍稍做了一些demo. zT ...
- 题解 UVA12206 【Stammering Aliens】
终于A了这道题啊(坑啊) 教练说:这道题不能用map吧,复杂度不一个O(nlogn)吗 于是我就一直想不出来,然后看题解代码,一看就是map... 所以我就在想,那复杂度是不是也不是O(nlogn)呢 ...
- IDEA中编写脚本并运行shell脚本
IDEA中编写脚本并运行shell脚本 来自 <https://blog.csdn.net/u012443641/article/details/81295999>
- String spilt时转义特殊字符【转】
在使用String.split方法分隔字符串时,分隔符如果用到一些特殊字符,可能会得不到我们预期的结果. 我们经常使用public String[] split(String regex)方法来拆分一 ...
- 【转】C#正则表达式教程和示例
[转]C#正则表达式教程和示例 有一段时间,正则表达式学习很火热很潮流,当时在CSDN一天就能看到好几个正则表达式的帖子,那段时间借助论坛以及Wrox Press出版的<C#字符串和正则表达式参 ...
- mysql-过程与函数
一.过程与函数简介 过程与函数是命名的PL/SQL块(也是用户的方案对象),被编译后存储在数据库中,以备执行.因此,其他PL/SQL块可以按名称来使用他们.所以可以将商业逻辑.企业规划写成函数或过程保 ...
- Windows server 2008 布署FTP服务器实例(适用于阿里云)!
Windows server 2008 布署FTP服务器实例(适用于阿里云). 1.打开管理.配置-用户-新建用户,如:ftp_user,并设置password.选择永只是期和password不能更改 ...
- [poj 2480] Longge's problem 解题报告 (欧拉函数)
题目链接:http://poj.org/problem?id=2480 题目大意: 题解: 我一直很欣赏数学题完美的复杂度 #include<cstring> #include<al ...
- 美国人教你这样用Google,你真的会变特工
转自微博:黑客师: 用了这么久的谷歌,今天才发现. 第一篇 在搜索框上输入:“indexof/”inurl:lib 再按搜索你将进入许多图书馆,并且一定能下载自己喜欢的书籍. 在搜索框上输入:“ind ...