【搜索】C_LQ_二人寻宝(判边界 + 统计 obs)

一、Problem

JM最近比较闲,迷上了一个寻宝游戏,她发觉这个游戏有一个必胜策略, 但是这个策略需要经过一番复杂的计算推演,她需要擅长编程的你帮她找到必胜策略。

游戏规则是这样的,有一个 n∗m 的迷宫,迷宫中有一个宝藏,你可以从迷宫外任意一点进入迷宫

但是通向宝藏的路上可能有一些障碍,如果有障碍,则JM和她的对手都必须轮流清理障碍,每次只能清理一个,如果没有障碍了(“没有障碍”是指宝藏的上下左右四个方位至少有一个方向没有障碍), 则可直接拿到宝藏。现在JM需要知道她应该先开始还让对手先开始。

1
3 3
2 1 2
1 -1 1
2 1 2
JM Second

1
3 2
1 1
1 -1
1 1
JM First

数据范围
在这里插入图片描述

二、Solution

方法一:判断

  • 判断宝藏 -1 是否在边界上,若是,则先手赢。
  • 障碍的个数 obs 如果是偶数后手必胜;否则,先手必胜。
    • 为什么呢?

未知错误:为什么输出和答案一样,不对的…

import java.util.*;
import java.math.*;
import java.io.*;
public class Main{
	static class Solution {
		int[][] g;
		int R, C;
		void init() {
			Scanner sc = new Scanner(new BufferedInputStream(System.in));
			int T = sc.nextInt();
			while (T-- > 0) {
				R = sc.nextInt(); C = sc.nextInt();
				g = new int[R][C];
				int obs = 0;
				int x = 0, y = 0;
				for (int i = 0; i < R; i++) {
					for (int j = 0; j < C; j++) {
						g[i][j] = sc.nextInt();
						if (g[i][j] != -1) obs += g[i][j];
						else {x = i; y = j;}
					}
				}
				boolean b = false;
    			if (x == 0 || x == R-1) b = true;
    			if (y == 0 || y == C-1) b = true;
    			if (b) System.out.println("JM First");
    			else   System.out.println(obs % 2 == 0 ? "JM Second" : "JM First");
			}
		}
	}
    public static void main(String[] args) throws IOException {  
        Solution s = new Solution();
		s.init();
    }
}

复杂度分析

  • 时间复杂度: O ( R × C ) O(R × C)
  • 空间复杂度: O ( R × C ) O(R × C)

方法二:dfs

不知道为什么用 dfs 判一下,可以过掉原来的方法一过不了的第三个测试用例…

理解一下这两句代码…

for (int i = 0; i < R; i++) b |= vis[i][0] | vis[i][C-1];
for (int i = 0; i < C; i++) b |= vis[0][i] | vis[R-1][i];
import java.util.*;
import java.math.*;
import java.io.*;
public class Main{
	static class Solution {
		int[][] g;
		int R, C;
		final int[][] dir = { {1,0},{0,-1},{0,1},{-1,0} };
		boolean[][] vis;
		
		void dfs(int x, int y) {
			vis[x][y] = true;
			for (int k = 0; k < 4; k++) {
				int tx = x + dir[k][0];
				int ty = y + dir[k][1];
				if (tx < 0 || tx >= R || ty < 0 || ty >= C || vis[tx][ty] || g[tx][ty] > 0)
					continue;
				dfs(tx, ty);
			}
		}
		void init() {
			Scanner sc = new Scanner(new BufferedInputStream(System.in));
			int T = sc.nextInt();
			while (T-- > 0) {
				R = sc.nextInt(); C = sc.nextInt();
				g = new int[R][C];
				int obs = 0;
				int x = 0, y = 0;
				for (int i = 0; i < R; i++) {
					for (int j = 0; j < C; j++) {
						g[i][j] = sc.nextInt();
						if (g[i][j] != -1) obs += g[i][j];
						else {x = i; y = j;}
					}
				}
				vis = new boolean[R][C];
				dfs(x, y);
				boolean b = false;
				for (int i = 0; i < R; i++) b |= vis[i][0] | vis[i][C-1];
				for (int i = 0; i < C; i++) b |= vis[0][i] | vis[R-1][i];
				
    			if (b) 	System.out.println("JM First");
    			else 	System.out.println(obs % 2 == 0 ? "JM Second" : "JM First");
			}
		}
	}
    public static void main(String[] args) throws IOException {  
        Solution s = new Solution();
		s.init();
    }
}

复杂度分析

  • 时间复杂度: O ( R × C ) O(R × C)
  • 空间复杂度: O ( R × C ) O(R × C)
原创文章 787 获赞 314 访问量 5万+

猜你喜欢

转载自blog.csdn.net/qq_43539599/article/details/105880276
obs