P4289 [HAOI2008] Mobile Toys
Bidirectional bfs+ State compression + memory Search
The two-way BFS is used to optimize the BFS, and each time a BFS is found on one side with a small number of expandable nodes , the first contact point is the shortest path.
Matrix range only 4*4 size, we can easily think of using binary number to compress its state, to facilitate the solution.
Since turn into binary, size and <2^17, then you can addend group for memory
Don't forget the qwq when the starting point is the same.
#include <iostream>#include<cstdio>#include<queue>#include<cstring>using namespacestd;structdata{intZip,step;};intans,rec1[65538],rec2[65538]; Rec: Memory Queue<data> h[2]; Represents the BFS queue inline from the start/end point, respectivelyvoidCheckintTo,intP,data x) {//Check whether the point meets the criteriaif(rec1[to]!=-1){ if(rec2[to]!=p) ans=rec1[to]+x.step+1and//If the point has been found in the opposite direction, then the optimal solution has been obtained}Else{Rec1[to]=x.step+1, rec2[to]=p; H[p].push (data) {To,x.step+1}); }}voidOutputintt) {//Check with, return 10 binary number to 4*4 binary matrix cout<<"---\ n"; inth[ +]; for(intK=t,i= the; i>=0;-I.) h[i]=k&1, k>>=1; for(intI=0;i<4;++i) { for(intj=i*4; j<=i*4+3; ++j) cout<<H[j]; cout<<Endl; } cout<<"---\ n";} InlinevoidBFs () {intP= (h[0].size () >h[1].size ()), now=(H[p].front ()). Step;//Find one side of the node that can be scaled less, and only extend the first layer while(!H[p].empty ()) {Data x=H[p].front (); if(x.step!=now| | Ans Break; H[p].pop (); intk=1, to; for(intI=1;i<65536; i<<=1,++k) {//using a binary number to represent the transfer processif(! (X.zip&i))Continue; if(k%4!=0&& (!) ( x.zip& (i<<1))) {//left to=x.zip-i+ (i<<1); Check (to,p,x); } if(k%4!=1&& (!) ( x.zip& (i>>1))) {//Right to=x.zip-i+ (i>>1); Check (to,p,x); } if(k>4&& (!) ( x.zip& (i>>4))) {//down to=x.zip-i+ (i>>4); Check (to,p,x); } if(k< -&& (!) ( x.zip& (i<<4))) {//Up to=x.zip-i+ (i<<4); Check (to,p,x); } } }}intMain () {memset (REC1,-1,sizeof(REC1)); Charq[6];inttot1=0, tot2=0; for(intI=1; i<=4;++i) {//matrix turns into decimal number cin>>Q; for(intj=0; j<=3; ++j) tot1+=q[j]- -, tot1<<=1; }TOT1>>=1;//Note the final move to the right one h[0].push (data) {TOT1,0}); rec1[tot1]=0; rec2[tot1]=0; for(intI=1; i<=4;++i) {cin>>Q; for(intj=0; j<=3; ++j) tot2+=q[j]- -, tot2<<=1; }tot2>>=1; h[1].push (data) {Tot2,0}); rec1[tot2]=0; rec2[tot2]=1; while(!ans&&tot1!=Tot2) BFS (); Pay attention to the special sentence printf ("%d", ans); return 0;}
P4289 [HAOI2008] Mobile toys