萌新求助搜索题
查看原帖
萌新求助搜索题
114914
一只书虫仔楼主2021/10/5 14:52

代码能力为 0 的萌新求助

/*
dfs 搜索,考虑下一个没有颜色的格子时:
- 花费 2 金币让他变得有颜色
- 枚举变成红色还是变成黄色
下一个有颜色的格子时:
- 直接走过去
当正处于没有颜色的格子时:
- 向四处搜索一个有颜色的并走过去
- 如果除了来时的格子没有有颜色的,则回溯

但总感觉这题貌似可以贪心 ……
但感觉贪心很容易假
*/

#include <bits/stdc++.h>

using namespace std;

int m, n;
int a[105][105];
int ans = 0x3f3f3f3f;
bool reach = false;
bool vis[105][105];

void dfs (int fx, int fy, int x, int y, int v, bool isnon) {
	printf("fx = %d fy = %d x = %d y = %d\n", fx, fy, x, y);
	if (v > ans) return;
	if (x == m && y == m) {
		ans = min(ans, v);
		reach = true;
		return;
	}
	if (y > 1)
		if (!(fx == x && fy == y - 1) && !vis[x][y - 1]) {
			if (!a[x][y - 1] && !isnon) {
				a[x][y - 1] = 1;
				vis[x][y - 1] = true;
				dfs(x, y, x, y - 1, v + 2, true);
				a[x][y - 1] = 2;
				dfs(x, y, x, y - 1, v + 2, true);
				a[x][y - 1] = 0;
				vis[x][y - 1] = false;
			}
			vis[x][y - 1] = true;
			if (!(a[x][y - 1] != a[x][y] && isnon) && a[x][y - 1])
				dfs(x, y, x, y - 1, v + int(a[x][y - 1] != a[x][y]), false);
			vis[x][y - 1] = false;
		}
	if (y < m)
		if (!(fx == x && fy == y + 1) && !vis[x][y + 1]) {
			if (!a[x][y + 1] && !isnon) {
				a[x][y + 1] = 1;
				vis[x][y + 1] = true;
				dfs(x, y, x, y + 1, v + 2, true);
				a[x][y + 1] = 2;
				dfs(x, y, x, y + 1, v + 2, true);
				a[x][y + 1] = 0;
				vis[x][y + 1] = false;
			}
			vis[x][y + 1] = true;
			if (!(a[x][y + 1] != a[x][y] && isnon) && a[x][y + 1])
				dfs(x, y, x, y + 1, v + int(a[x][y + 1] != a[x][y]), false);
			vis[x][y + 1] = false;
		}
	if (x > 1)
		if (!(fx == x - 1 && fy == y) && !vis[x - 1][y]) {
			if (!a[x - 1][y] && !isnon) {
				a[x - 1][y] = 1;
				vis[x - 1][y] = true;
				dfs(x, y, x - 1, y, v + 2, true);
				a[x - 1][y] = 2;
				dfs(x, y, x - 1, y, v + 2, true);
				a[x - 1][y] = 0;
				vis[x - 1][y] = false;
			}
			vis[x - 1][y] = true;
			if (!(a[x - 1][y] != a[x][y] && isnon) && a[x - 1][y])
				dfs(x, y, x - 1, y, v + int(a[x - 1][y] != a[x][y]), false);
			vis[x - 1][y] = false;
		}
	if (x < m)
		if (!(fx == x + 1 && fy == y) && !vis[x + 1][y]) {
			if (!a[x + 1][y] && !isnon) {
				a[x + 1][y] = 1;
				vis[x + 1][y] = true;
				dfs(x, y, x + 1, y, v + 2, true);
				a[x + 1][y] = 2;
				dfs(x, y, x + 1, y, v + 2, true);
				a[x + 1][y] = 0;
				vis[x + 1][y] = false;
			}
			vis[x + 1][y] = true;
			if (!(a[x + 1][y] != a[x][y] && isnon) &&a[x + 1][y])
				dfs(x, y, x + 1, y, v + int(a[x + 1][y] != a[x][y]), false);
			vis[x + 1][y] = false;
		}
	// left
	// right
	// up
	// down
	return;
}

// (fx, fy) 这个格子从哪里来的
// (x, y) 目前的格子是什么
// v 走到这个格子用了多少金币
// isnon 原来这个格子是否无颜色

int main () {
	scanf("%d%d", &m, &n);
	for (int i = 1, x, y, c; i <= n; i++) {
		scanf("%d%d%d", &x, &y, &c);
		a[x][y] = c + 1;
	}
	vis[1][1] = true;
	dfs(0, 0, 1, 1, 0, false);
	if (!reach) puts("-1");
	else printf("%d\n", ans);
	return 0;
}

// c = 1 red
// c = 2 yellow

样例输出 77,自己构造了几组数据都是对的。

2021/10/5 14:52
加载中...