题意:开锁,给出了密码的初始状态,和目标状态,这里密码是固定的四位,每次可以把某一位加一或者减一,再者交换相邻的两位,最左边与最右边是不相邻的
解法:BFS,实现操作的函数即可
#include<iostream> #include<cstdlib> #include<cmath> #include<algorithm> #include<cstring> #include<cstdio> #include<queue> #include<set> #include<stack> #define cl(a,b) memset(a,b,sizeof(a)); #define LL long long #define P pair<int,int> #define X first #define Y second #define pb push_back #define out(x) cout<<x<<endl; using namespace std; const int maxn=9999+10; const int inf=9999999; int init,target; int change(int num,int pos,int kind){ int tmp[4]; int i=0; while(num){ tmp[i++]=num%10; num/=10; } reverse(tmp,tmp+4); if(kind==1){///add tmp[pos]++; if(tmp[pos]==10){ tmp[pos]=1; } } else { tmp[pos]--; if(tmp[pos]==0){ tmp[pos]=9; } } return tmp[0]*1000+tmp[1]*100+tmp[2]*10+tmp[3]; } int swapnum(int num,int a,int b){ int tmp[4]; int i=0; while(num){ tmp[i++]=num%10; num/=10; } reverse(tmp,tmp+4); swap(tmp[a],tmp[b]); return tmp[0]*1000+tmp[1]*100+tmp[2]*10+tmp[3]; } bool vis[maxn]; int step[maxn]; int bfs(){ cl(vis,false); cl(step,0); queue<int> q; q.push(init); vis[init]=true; while(!q.empty()){ int tmp=q.front();q.pop(); if(tmp==target){ return step[tmp]; } for(int i=0;i<=3;i++){///add int x=change(tmp,i,1); if(!vis[x]){ vis[x]=true; step[x]=step[tmp]+1; q.push(x); } } for(int i=0;i<=3;i++){ int x=change(tmp,i,0); if(!vis[x]){ vis[x]=true; step[x]=step[tmp]+1; q.push(x); } } for(int i=0;i<3;i++){ int x=swapnum(tmp,i,i+1); if(!vis[x]){ vis[x]=true; step[x]=step[tmp]+1; q.push(x); } } } return -1; } int main(){ int T; scanf("%d",&T); while(T--){ scanf("%d%d",&init,&target); printf("%d\n",bfs()); } return 0; }
版权声明:本文为博主原创文章,未经博主允许不得转载。
时间: 2024-11-09 00:48:55