A good question has been ruined by me.
The meaning of a Chinese Question is needless to say. Compress the key status: 01 indicates there is a key 1, 10 indicates there is a key 2, 11 represents keys 1 and 2 ............................... ....................................
The thinking was wrong at two points and it took a morning:
1. to determine whether a vertex is in the queue, except for the precondition, whether the vertex status is updated (that is, whether a key is obtained ), after the update status does not appear, you can join ............ in the first place, I did not consider the status issue and joined the team directly. There will be re-queries walking around at two points.
2. there may be multiple keys in the same way. In the first writing, you may encounter a key that has already been taken. If the key is not in the queue, the problem may occur: if there is the same key on the road that just reaches the end, then it becomes inaccessible.
Therefore, duplicate keys do not need to be considered.
# Include <cstdio> # include <iostream> # include <cmath> # include <cstring> # include <algorithm> using namespace std; int n, m, head, tail, T; char map [33] [33]; int dp [33] [33] [1 <10]; int dirx [] = {1,-1, 0 }; int diry [] = {0, 0, 1,-1}; struct node {int x, y; int buff;} q [1111111], st, end; void init () {memset (dp,-1, sizeof (dp); head = 0; tail = 0;} bool go (int x, int y) {if (x <0 | x> = n | y <0 | y> = M) return false; if (map [x] [y] = '*') return false; return true;} int bfs () {q [head ++] = st; dp [st. x] [st. y] [st. buff] = 0; while (head! = Tail) {node t = q [tail ++]; node tt; if (t. x = end. x & t. y = end. y) {if (T> dp [t. x] [t. y] [t. buff]) return dp [t. x] [t. y] [t. buff]; else return-1;} if (dp [t. x] [t. y] [t. buff]> = T) return-1; for (int I = 0; I <4; I ++) {tt. x = t. x + dirx [I]; tt. y = t. y + diry [I]; tt. buff = t. buff; if (go (tt. x, tt. y) {if (map [tt. x] [tt. y]> = 'A' & map [tt. x] [tt. y] <= 'J') {int move = map [tt. x] [tt. y]-'A'; if (t. buff> Move) & 1) = 0) continue;} else if (map [tt. x] [tt. y]> = 'A' & map [tt. x] [tt. y] <= 'J') {int move = map [tt. x] [tt. y]-'A'; // if (t. buff> move) & 1) continue; // tt. buff = t. buff | (1 <move);} if (dp [tt. x] [tt. y] [tt. buff] =-1) {dp [tt. x] [tt. y] [tt. buff] = dp [t. x] [t. y] [t. buff] + 1; q [head ++] = tt ;}}} return-1;} int main () {while (scanf ("% d", & n, & m, & T )! = EOF) {init (); for (int I = 0; I <n; I ++) scanf ("% s", map [I]); for (int I = 0; I <n; I ++) for (int j = 0; j <m; j ++) {if (map [I] [j] = '@') {st. x = I; st. y = j; st. buff = 0;} if (map [I] [j] = '^') {end. x = I; end. y = j; end. buff = 0 ;}} printf ("% d \ n", bfs () ;}return 0 ;}