At the beginning, I was shocked to see this question. The first thought was that I could not record the points that had passed by. Once the record was made, if the key was on the opposite side and the door was on this side, I would not be able to get the key back;
However, if no record is recorded, it would not be a chaos in the whole map, absolutely time out, or even an endless loop;
After that, I thought about how to record the status of each vertex when each vertex is in the queue, that is, whether or not I have obtained the key or what kind of key to get, there is no need to join the team when the two vertices are in the same status. This is indeed a feasible method. However, when I think of it, I suddenly think that I want to save 16 statuses for each vertex, the memory will definitely be exploding, and the results will be suspended, so I can't find any other way ......
I checked it and found that the original record status was saved using bitwise operations. I knew this was a problem. I also used bitwise operations to save whether a number exists, I didn't even think of the result.
In this way, a three-dimensional array is opened. The flag [101] [101] [16] records the status of each vertex. Besides coordinates, a vertex has no key, how many keys are there, and each bit stores the state of a key, a total of 16 States
Assume that the keys/B, Y, R, and g are saved in the first, second, third, and fourth bits of binary respectively. Flag & 1 = 1 indicates that the State Key B already exists, when the key B is obtained, the flag | = 1 is recorded.
# Include <iostream> # include <queue> using namespace STD; char map [101] [101]; int dir [4] [2] = }, {-101}, {101}, {0,-1 }}, n, m; int flag [] [] [16]; // B, y, r, G: 1, 2, 4, 8 struct node {int X, Y, CNT, V; node (INT _ x = 0, int _ y = 0, int _ CNT = 0, int _ v = 0): X (_ x), y (_ y), CNT (_ CNT), V (_ v ){}; friend bool operator <(const node & A, const node & B) {return. CNT> B. CNT ;}; node F; bool OK (int I, Int J, int VA) {If (Map [I] [J] = 'B' & (va & 1) retu Rn true; If (Map [I] [J] = 'y' & (va & 2) return true; if (Map [I] [J] = 'R' & (va & 4) return true; if (Map [I] [J] = 'G' & (va & 8) return true; return false;} int BFS () {flag [F. x] [F. y] [F. v] = 1; priority_queue <node> q; q. push (f); While (! Q. empty () {node T = Q. top (); q. pop (); For (int K = 0; k <4; k ++) {int I = T. X + dir [k] [0]; Int J = T. Y + dir [k] [1]; if (I <n & I> = 0 & J <M & J> = 0 & map [I] [J]! = '#') {If (OK (I, j, T. V )&&! Flag [I] [J] [T. v]) {flag [I] [J] [T. v] = 1; q. push (node (I, j, T. CNT + 1, T. v);} else if (Map [I] [J] = 'B '&&! Flag [I] [J] [T. v | 1]) {flag [I] [J] [T. v | 1] = 1; q. push (node (I, j, T. CNT + 1, T. v | 1);} else if (Map [I] [J] = 'y '&&! Flag [I] [J] [T. v | 2]) {flag [I] [J] [T. v | 2] = 1; q. push (node (I, j, T. CNT + 1, T. v | 2);} else if (Map [I] [J] = 'R '&&! Flag [I] [J] [T. v | 4]) {flag [I] [J] [T. v | 4] = 1; q. push (node (I, j, T. CNT + 1, T. v | 4);} else if (Map [I] [J] = 'G '&&! Flag [I] [J] [T. v | 8]) {flag [I] [J] [T. v | 8] = 1; q. push (node (I, j, T. CNT + 1, T. v | 8);} else if (Map [I] [J] = '. '&&! Flag [I] [J] [T. v]) {flag [I] [J] [T. v] = 1; q. push (node (I, j, T. CNT + 1, T. v);} else if (Map [I] [J] = 'X') return T. CNT + 1 ;}}return 0 ;}int main () {While (CIN >>> n >> M & (N | M )) {for (INT I = 0; I <n; I ++) for (Int J = 0; j <m; j ++) {CIN> map [I] [J]; If (Map [I] [J] = '*') F. X = I, F. y = J;} f. CNT = 0; F. V = 0; Map [F. x] [F. y] = '. '; memset (flag, 0, sizeof (FLAG); int T = BFS (); If (t) cout <"escape possible in" <t <"steps. "<Endl; else cout <" the poor student is trap Ped! "<Endl;} return 0 ;}