POJ 1077 Eight
题意:经典的八数码=3=
3*3的格子,里面有1~8这8个数字,还有一个空格x,移动空格的位置,直到移到1~8按顺序排好,输出移动的序列。
解法:看到题果断写了个广搜……然后T了……百度了一下说广搜虽然慢了点但是也是可以过的嘛……默默看了眼自己代码……唔……好像他们都不是用string路径的……
实在懒得改了,学个新做法吧,哦吼吼吼这个A*看起来很神奇啊……学一下学一下
600ms+过了……嗯……跟别人广搜一个时间啊……_(:з」∠)_实在不想改记路径的方法啊……
A*我觉得就是一个更聪明的广搜……每个状态的权值为每个数到最终状态的曼哈顿距离之和加上已走过的步长,用优先队列维护……
还有就是每个状态序列可以转换成一个排列的id……涨姿势了0v0
代码:
#include<stdio.h>
#include<iostream>
#include<algorithm>
#include<string>
#include<string.h>
#include<math.h>
#include<limits.h>
#include<time.h>
#include<stdlib.h>
#include<map>
#include<queue>
#include<set>
#include<stack>
#include<vector>
#define LL long long using namespace std; int fac[] = { 1, 1, 2, 6, 24, 120, 720, 5040, 40320, 362880 };
int order(vector <int> v) {
int i, j, temp, num;
num = 0;
for (i = 0; i < 8; i++) {
temp = 0;
for (j = i + 1; j < 9; j++) {
if (v[j] < v[i])
temp++;
}
num += fac[v[i] -1] * temp;
}
return num;
}
bool vis[400000];
int dir1[4][2] = {-1, 0, 1, 0, 0, -1, 0, 1};
char dir2[] = "udlr";
struct node
{
vector <int> v;
string path;
node(vector <int> tv, string tpath)
{
v = tv;
path = tpath;
}
node() {}
bool operator < (const node &tmp) const
{
int sum1 = 0, sum2 = 0;
for(int i = 0; i < 9; i++)
sum1 += abs((v[i] - 1) / 3 - i / 3) + abs((v[i] - 1) % 3 - i % 3);
for(int i = 0; i < 9; i++)
sum2 += abs((tmp.v[i] - 1) / 3 - i / 3) + abs((tmp.v[i] - 1) % 3 - i % 3);
return sum1 + path.size() > sum2 + tmp.path.size();
}
};
string bfs(vector <int> st)
{
memset(vis, 0, sizeof vis);
vis[order(st)] = 1;
priority_queue <node> q;
q.push(node(st, ""));
while(!q.empty())
{
node tmp = q.top();
if(order(tmp.v) == 0) return tmp.path;
q.pop();
int sx, sy;
for(int i = 0; i < 3; i++)
for(int j = 0; j < 3; j++)
if(tmp.v[i * 3 + j] == 9)
{
sx = i;
sy = j;
}
for(int i = 0; i < 4; i++)
{
int tx = sx + dir1[i][0], ty = sy + dir1[i][1];
if(tx < 0 || tx > 2 || ty < 0 || ty > 2) continue;
swap(tmp.v[tx * 3 + ty], tmp.v[sx * 3 + sy]);
int id = order(tmp.v);
if(!vis[id])
{
vis[id] = 1;
q.push(node(tmp.v, tmp.path + dir2[i]));
}
swap(tmp.v[tx * 3 + ty], tmp.v[sx * 3 + sy]);
}
}
return "unsolvable";
}
int main()
{
char input[2];
while(~scanf("%s", input))
{
vector <int> v;
if(input[0] == 'x')
v.push_back(9);
else
v.push_back(input[0] - '0');
for(int i = 0; i < 8; i++)
{
scanf("%s", input);
if(input[0] == 'x')
v.push_back(9);
else
v.push_back(input[0] - '0');
}
int sum = 0;
for(int i = 1; i < 9; i++)
for(int j = 0; j < i; j++)
if(v[i] != 9 && v[j] != 9 && v[i] < v[j]) sum++;
if((sum & 1) == 0)
cout << bfs(v) << endl;
else
puts("unsolvable1");
}
return 0;
}
POJ 1077 Eight的更多相关文章
- 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 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 ...
- POJ 1077 && HDU 1043 Eight A*算法,bfs,康托展开,hash 难度:3
http://poj.org/problem?id=1077 http://acm.hdu.edu.cn/showproblem.php?pid=1043 X=a[n]*(n-1)!+a[n-1]*( ...
- hdu 1043 pku poj 1077 Eight (BFS + 康拓展开)
http://acm.hdu.edu.cn/showproblem.php?pid=1043 http://poj.org/problem?id=1077 Eight Time Limit: 1000 ...
- poj 1077 Eight(双向bfs)
题目链接:http://poj.org/problem?id=1077 思路分析:题目要求在找出最短的移动路径,使得从给定的状态到达最终状态. <1>搜索算法选择:由于需要找出最短的移动路 ...
- poj 1077 Eight (八数码问题——A*+cantor展开+奇偶剪枝)
题目来源: http://poj.org/problem?id=1077 题目大意: 给你一个由1到8和x组成的3*3矩阵,x每次可以上下左右四个方向交换.求一条路径,得到12345678x这样的矩阵 ...
- BFS(八数码) POJ 1077 || HDOJ 1043 Eight
题目传送门1 2 题意:从无序到有序移动的方案,即最后成1 2 3 4 5 6 7 8 0 分析:八数码经典问题.POJ是一次,HDOJ是多次.因为康托展开还不会,也写不了什么,HDOJ需要从最后的状 ...
- HDU 1403 Eight&POJ 1077(康拖,A* ,BFS,双广)
Eight Time Limit: 10000/5000 MS (Java/Others) Memory Limit: 65536/32768 K (Java/Others) Total Submis ...
随机推荐
- java.util.ResourceBundle
转载自: http://lavasoft.blog.51cto.com/62575/184605 这个类提供软件国际化的捷径.通过此类,可以使您所编写的程序可以: 轻松地本地化或翻译 ...
- POJ 1701
/* Every tenant went up N floors would make the dissatisfied degree rise N * a + 0.5 * N * (N - 1) d ...
- D&F学数据结构系列——插入排序
插入排序(insertion sort) 插入排序由P-1趟(pass)排序组成.对于P=1趟到P=N-1趟,插入排序保证从位置0到位置P-1上的元素为已排序状态.插入排序利用了这样的事实:位置0到位 ...
- SDUT 1220 完美数
完美数 Time Limit: 1000ms Memory limit: 65536K 题目描述 任何一个自然数的约数中都有1和它本身,我们把小于它本身的因数叫做这个自然数的真约数. 如6的所有真 ...
- 1051 Wooden Sticks
Wooden Sticks Time Limit: 2000/1000 MS (Java/Others) Memory Limit: 65536/32768 K (Java/Others)Tot ...
- utf-8中的汉字占用多少字节
转载:http://blog.csdn.net/chummyhe89/article/details/7777613 占2个字节的:〇 占3个字节的:基本等同于GBK,含21000多个汉字 占4个字节 ...
- Sina App Engine(SAE)入门教程(3)-KVDB使用
简介 因为传统关系型数据库在分布式环境下表现的扩展性不足等缺点,近年来NoSQL的概念渐渐成为业界关注的焦点,越来越多的技术人员也习惯于使用NoSQL数据库进行日常开发,SAE为了应对这种新需求,也进 ...
- React事件处理函数的bind复用和name复用
一.bind复用 <!DOCTYPE html> <html lang="zh-cn"> <head> <meta charset=&qu ...
- Ping 命令
Ping”命令是我们在判断网络故障常用的命令 它是用来检查网络是否通畅或者网络连接速度的命令. 它所利用的原理是这样的:网络上的机器都有唯一确定的IP地址,我们给目标IP地址发送一个数据包, 对方就要 ...
- 使用 Spring 3 来创建 RESTful Web Services(转)
使用 Spring 3 来创建 RESTful Web Services 在 Java™ 中,您可以使用以下几种方法来创建 RESTful Web Service:使用 JSR 311(311)及其参 ...