The Morning after Halloween UVA

来源:互联网 发布:excel自动生成数据 编辑:程序博客网 时间:2024/06/05 04:03

按照紫书的做法,创建两个对列,进行双向的BFS搜索,即可。具体实现见如下代码:

#include<iostream>#include<vector>#include<string>#include<set>#include<stack>#include<queue>#include<map>#include<algorithm>#include<cmath>#include<iomanip>#include<cstring>#include<sstream>#include<cstdio>#include<deque>using namespace std;int w, h, n;int dx[] = {0,1,-1,0,0};int dy[] = {0,0,0,1,-1};string *area;int Start[3], End[3];int Length[270];int Edge[270][270];int d1[270][270][270], d2[270][270][270];int ID(int a, int b, int c){return (a << 16) | (b << 8) | (c);}bool feasible(int a,int a1,int b,int b1){if (a1 == b1 || (a==b1&&a1==b)) return false;return true;}int D_BFS(){queue<int> q1, q2;q1.push(ID(Start[0],Start[1],Start[2]));q2.push(ID(End[0], End[1], End[2]));memset(d1, -1, sizeof(d1));memset(d2, -1, sizeof(d2));d1[Start[0]][Start[1]][Start[2]] = 0;d2[End[0]][End[1]][End[2]] = 0;while (!q1.empty()&&!q2.empty()){queue<int> next_s;if (q1.size() < q2.size()){while (!q1.empty()){int front = q1.front(); q1.pop();int a, b, c;a = (front >> 16) & 0xff; b = (front >> 8) & 0xff; c = (front)& 0xff;for (int i = 0; i < Length[a]; i++){int a1 = Edge[a][i];for (int j = 0; j < Length[b]; j++){int b1 = Edge[b][j];if (!feasible(a, a1, b, b1)) continue;for (int k = 0; k < Length[c]; k++){int c1 = Edge[c][k];if (!feasible(a, a1, c, c1) || !feasible(b, b1, c, c1) || d1[a1][b1][c1] != -1) continue;d1[a1][b1][c1] = d1[a][b][c] + 1;if (d2[a1][b1][c1] != -1) return d1[a1][b1][c1] + d2[a1][b1][c1];if (a1 == End[0] && b1 == End[1] && c1 == End[2]) return d1[a1][b1][c1];next_s.push(ID(a1, b1, c1));}}}}q1 = next_s;}else{while (!q2.empty()){int front = q2.front(); q2.pop();int a, b, c;a = (front >> 16) & 0xff; b = (front >> 8) & 0xff; c = (front)& 0xff;for (int i = 0; i < Length[a]; i++){int a1 = Edge[a][i];for (int j = 0; j < Length[b]; j++){int b1 = Edge[b][j];if (!feasible(a, a1, b, b1)) continue;for (int k = 0; k < Length[c]; k++){int c1 = Edge[c][k];if (!feasible(a, a1, c, c1) || !feasible(b, b1, c, c1) || d2[a1][b1][c1] != -1) continue;d2[a1][b1][c1] = d2[a][b][c] + 1;if (d1[a1][b1][c1] != -1) return d1[a1][b1][c1] + d2[a1][b1][c1];if (a1 == Start[0] && b1 == Start[1] && c1 == Start[2]) return d2[a1][b1][c1];next_s.push(ID(a1, b1, c1));}}}}q2 = next_s;}}return -1;}int main(){while (cin >> w >> h >> n){if (w == 0 && h == 0 && n == 0) break;string del; getline(cin, del);area = new string[h];for (int i = 0; i < h; i++) getline(cin, area[i]);int index = 0;int id[270][270], x[270], y[270];memset(id,-1,sizeof(id));memset(x, -1, sizeof(x));memset(y, -1, sizeof(y));for (int i = 0; i < h; i++){for (int j = 0; j < w; j++){if (area[i][j] != '#'){x[index] = i; y[index] = j; id[i][j] = index;if (area[i][j] >= 'a'&&area[i][j] <= 'z') Start[area[i][j] - 'a']=index;if (area[i][j] >= 'A'&&area[i][j] <= 'Z') End[area[i][j] - 'A'] = index;index++;}}}memset(Length,0,sizeof(Length));for (int i = 0; i < index; i++){int tx = x[i], ty = y[i];for (int j = 0; j < 5; j++){int newx = tx + dx[j], newy = ty + dy[j];if (newx >= 0 && newx < h&&newy >= 0 && newy < w&&area[newx][newy] != '#'){Edge[i][Length[i]] = id[newx][newy];Length[i]++;}}}if (n <= 1){Start[1] = End[1] = index;Length[index] = 1;Edge[index][0] = index;index++;}if (n <= 2){Start[2] = End[2] = index;Length[index] = 1;Edge[index][0] = index;index++;}cout << D_BFS() << endl;}return 0;}

原创粉丝点击