八数码问题<set的使用>bfs

来源:互联网 发布:手机阿里云os登录 编辑:程序博客网 时间:2024/05/19 18:48

the reason of failure:1、如何对0进行上下左右移动

用pos找到0在数组中的下标

可以定义dr[]={0,1,0,-1};dc[]={1,0,-1,0}.然后一个for4次的循环,r=pos/3+dr c=pos%3+dc

便能实现上下左右的移动

2、对于储存状态与查找,可以把数组存入set然后查找。

题意

八数码问题。编号为1~8的8个正方形滑块被摆成3行3列(有一个格子留空),如图7-
14所示。每次可以把与空格相邻的滑块(有公共边才算相邻)移到空格中,而它原来的位置
就成为了新的空格。给定初始局面和目标局面(用0表示空格),你的任务是计算出最少的
移动步数。如果无法到达目标局面,则输出-1。
图7-14 八数码问题举例


代码:

#include <iostream> #include <queue>#include <string.h>#include <set>using namespace std;struct ttt{int t;int a[9];};int str2[9];int dr[]={1,0,-1,0};int dc[]={0,1,0,-1};int main(){set<int>vis;freopen("in.txt","r",stdin);queue<ttt>qq; int n,r,c; int i,j,k,l,pos1,t1; ttt str1,str4,str3; cin >> n; for(i=0;i<n;i++){ for(j=0;j<9;j++) cin >> str1.a[j];   for(j=0;j<9;j++)   cin >> str2[j]; str1.t=0; qq.push(str1); int t1=0; while(!qq.empty()){ t1++; str3=qq.front();qq.pop(); if(memcmp(str3.a,str2,sizeof(str2))==0){ break;}  for(j=0;j<9;j++){ if(str3.a[j]==0){ pos1=j; break; } } str3.t++; for(j=0;j<4;j++){ r=pos1/3+dr[j]; c=pos1%3+dc[j]; memcpy(&str4,&str3,sizeof(str3)); if(r>=0&&r<3&&c<3&&c>=0){ str4.a[pos1]=str3.a[r*3+c]; str4.a[r*3+c]=0; int g=0; for(k=0;k<9;k++){ g=g*10+str4.a[k]; }// cout << g << endl; if(!vis.count(g)){ vis.insert(g); qq.push(str4);} } }  } if(memcmp(str3.a,str2,sizeof(str2))==0) cout << str3.t << endl; else cout << "-1" << endl; } return 0;}

2、用hash判重。

the reason of failure :1、hash需要把所有值都放入st[]这样一个大数组中才能找到之前是否存在里面,hash的mod尽量找一个大的素数。

2、关于memcmp与memcpy都是需要sizeof(a)写大小的。

代码:

#include <iostream>#include <queue>#include <string.h>using namespace std;struct ttt{int a[9],t;};const int hashsize =1000003;typedef int con[9];int head[5000000];int next[5000000];con st[50000000];int dr[]={0,1,-1,0};int dc[]={1,0,0,-1};int aa;ttt str1,str3,str4;int str2[9];int hash(con str5){int t1=0;for(int g=0;g<9;g++)t1=t1*10+str5[g];//cout << "t1=" << t1 << endl;return t1%hashsize;}int try_insert(int s){int h=hash(st[s]);int u=head[h];while(u){if(memcmp(st[u],st[s],sizeof(st[s]))==0)return 0;u=next[u];}head[h]=s;next[s]=u;return 1;}int main(){memset(head,0,sizeof(head));freopen("in.txt","r",stdin);queue<ttt>qq;int i,j,k,l;int r,c,pos1;long long g=1;for(i=0;i<9;i++)cin >> str1.a[i];for(i=0;i<9;i++)cin >> str2[i];str1.t=0;qq.push(str1);while(!qq.empty()){str3=qq.front();qq.pop();if(memcmp(str3.a,str2,sizeof(str2))==0)break;for(i=0;i<9;i++){if(str3.a[i]==0){pos1=i;break;}}str3.t++;for(i=0;i<4;i++){r=pos1/3+dr[i];c=pos1%3+dc[i];if(r>=0&&r<3&&c>=0&&c<3){str4=str3;str4.a[pos1]=str3.a[r*3+c];str4.a[r*3+c]=0;memcpy(st[g],str4.a,sizeof(st[g]));if(try_insert(g)){qq.push(str4);g++;}}}}if(memcmp(str3.a,str2,sizeof(str2))==0)cout << str3.t << endl;elsecout << "-1" << endl;return 0;}


0 0
原创粉丝点击