uva 10047(bfs)

题解:这题主要是bfs搜索时的是否搜索这个点的判定条件不太好写,参考了别人的思路写了一个,只要这个点是不同方向不同颜色经过的就可以重复经过,也就是有20种经过情况,只有都走过了才不再走这个点, 用了一个四维数组,记录点的坐标和颜色方向。

#include <stdio.h>
#include <string.h>
#include <queue>
using namespace std;
const int N = 50;

struct P {
	int x, y, face, color, time;
}p;
queue<P> q;
int row, col, flag, x1, x2, y1, y2, vis[N][N][4][5], face1, color1, time1;
char pos[N][N];
int flag1[4] = {-1, 0, 1, 0};
int flag2[4] = {0, 1, 0, -1};
void init() {
	memset(vis, 0, sizeof(vis));
	memset(pos, 0, sizeof(pos));
	face1 = x1 = x2 = y1 = y2 = color1 = time1 = 0;
	while (!q.empty())
		q.pop();
	flag = 0;
}

void bfs() {
	p.x = x1;
	p.y = y1;
	p.face = p.color = p.time = 0;
	q.push(p);
	vis[x1][y1][0][0] = 1;
	while (!q.empty()) {
		face1 = q.front().face;
		color1 = q.front().color;
		time1 = q.front().time;
		x1 = q.front().x;
		y1 = q.front().y;
		q.pop();
		
		if (x1 == x2 && y1 == y2 && color1 == 0) {
			flag = 1;
			return;
		}
		// right
		p.x = x1;
		p.y = y1;
		p.face = (face1 + 1) % 4;
		p.color = color1;
		p.time = time1 + 1;
		if (vis[p.x][p.y][p.face][p.color] == 0) {
			q.push(p);
			vis[p.x][p.y][p.face][p.color] = 1;
		}
		// left
		p.face = (face1 + 3) % 4;
		if (vis[p.x][p.y][p.face][p.color] == 0) {
			q.push(p);
			vis[p.x][p.y][p.face][p.color] = 1;
		}
		// go ahead
		// face up->0, right->1, down->2, left->3
		p.face = face1;
		p.color = (color1 + 1) % 5;
		p.x = x1 + flag1[face1];
		p.y = y1 + flag2[face1];

		if (p.x < 0 || p.x >= row || p.y < 0 || p.y >= col)
			continue;

		if (pos[p.x][p.y] != '#' && vis[p.x][p.y][p.face][p.color] == 0) {
			q.push(p);
			vis[p.x][p.y][p.face][p.color] = 1;
		}
	}
}

int main() {
	char c;
	int t = 1;
	while (scanf("%d%d", &row, &col) && (col || row)) {
		init();
		for (int i = 0; i < row; i++)
			for (int j = 0; j < col; j++) {
				scanf("%c", &c);
				if (c == '\n') {
					j--;
					continue;
				}
				pos[i][j] = c;
				if (pos[i][j] == 'S') {
					x1 = i;
					y1 = j;
				}
				if (pos[i][j] == 'T') {
					x2 = i;
					y2 = j;
				}
			}
		bfs();
		if (t != 1)
			printf("\n");
		printf("Case #%d\n", t++);
		if (flag)
			printf("minimum time = %d sec\n", time1);
		else
			printf("destination not reachable\n");
	}
	return 0;
}

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值