这个问题是一个基于图的广度优先搜索(BFS)问题,我们需要计算病毒感染所有座位上的人所需的时间。我们可以将每个座位视为图中的一个节点,而人与人之间的传播关系则可以视为边。以下是结合代码解决这个问题的步骤:
1. 初始化数据结构
dx和dy数组用于表示四个方向的移动(上下左右)。d数组用于存储每个座位的感染时间,初始化为0。boolean[][] st用于记录每个座位是否已经被访问过,以避免重复感染。
2. 构建图
int[][] dp存储每个座位上人的感染状态,其中1表示未戴口罩,可以直接被感染;2表示戴了口罩,需要额外的感染时间或被两个方向的人同时感染。
int[][] dp = new int[row_n+1][column_m+1];
for(int i=0;i<row_n;i++){
for(int j=0;j<column_m;j++){
dp[i][j] = 1; // 默认为1,表示未戴口罩
if(seats[i][j] == 1) dp[i][j]++; // 如果戴口罩,增加额外的感染时间
}
}
3. 广度优先搜索(BFS)
- 使用
Queue<Pair>来实现 BFS,从已感染的人开始,逐层扩展直到所有节点都被感染。 Pair类用于存储 BFS 中的节点和对应的感染时间。
class Pair{
int x,y,d;
public Pair(int x, int y, int d) {
super();
this.x = x;
this.y = y;
this.d = d;
}
}
- 在
bfs函数中,我们使用一个队列来存储待处理的节点,每个节点包含其坐标和当前的感染时间。
public static int bfs(int x,int y,int n,int m,int[][] dp){
boolean[][] st = new boolean[10001][10001];
Queue<Pair> p = new LinkedList<Pair>();
Arrays.fill(d, 0);
p.add(new Pair(x, y, 0));
int ans = 0;
while(p.size()>0) {
Pair pair = p.poll();
int x2 = pair.x,y2 = pair.y,d = pair.d;
if(!st[x2][y2]) {
st[x2][y2] = true;
ans = Math.max(ans, d); // 更新最大感染时间
for(int i=0;i<4;i++){
int x1 = x2 + dx[i],y1 = y2 + dy[i];
if(x1 >= 0 && x1 < n && y1 < m && y1 >= 0 && dp[x1][y1] > 0){
dp[x1][y1] --;
if(dp[x1][y1] == 0) {
p.add(new Pair(x1, y1, d + 1));
}
}
}
}
}
return ans;
}
4. 计算最大感染时间
- 在
bfs函数中,我们维护一个ans变量来记录最大的感染时间。 - 每次访问一个新的节点时,我们都会更新
ans。
5. 调用 bfs 函数
- 在
solution函数中,我们初始化dp数组,并调用bfs函数计算结果。
public static int solution(int row_n, int column_m, int[][] seats, int[] patient) {
int[][] dp = new int[row_n+1][column_m+1];
for(int i=0;i<row_n;i++){
for(int j=0;j<column_m;j++){
dp[i][j] = 1;
if(seats[i][j] == 1) dp[i][j]++;
}
}
int ans = bfs(patient[0],patient[1],row_n,column_m,dp);
return ans;
}
6. 主函数测试
- 在
main函数中,我们提供了几个测试用例来验证算法的正确性。
public static void main(String[] args) {
int[][] testSeats1 = {{0,1,1,1},{1,0,1,0},{1,1,1,1},{0,0,0,1}};
System.out.println(solution(4, 4, testSeats1, new int[]{2, 2}) == 6);
}
注意事项
- 确保在 BFS 中正确处理戴口罩的人,他们需要更多的时间或被多个方向的人同时感染。
- 在 BFS 中,如果一个座位上的人戴口罩,并且已经被感染,需要检查他们是否已经被周围的两个人感染,或者是否已经过了两秒钟。
- 最终的结果应该是所有座位都被感染时的最大时间。