避免淹死并到达目的地的最短时间
难度:
标签:
题目描述
代码结果
运行时间: 273 ms, 内存: 18.2 MB
// Leetcode 2814: 最短时间避免淹死并到达目的地
// 题目思路:
// 使用Java Stream处理相同的任务,重点在于流式处理集合数据。我们还是用Dijkstra算法,但通过流的方式管理优先队列。
import java.util.*;
import java.util.stream.*;
class Solution {
public int minimumTimeToAvoidDrowning(int[][] grid) {
int m = grid.length;
int n = grid[0].length;
int[][] directions = {{1, 0}, {-1, 0}, {0, 1}, {0, -1}};
int[][] time = new int[m][n];
for (int i = 0; i < m; i++) {
for (int j = 0; n; j++) {
time[i][j] = Integer.MAX_VALUE;
}
}
time[0][0] = grid[0][0];
PriorityQueue<int[]> pq = new PriorityQueue<>(Comparator.comparingInt(a -> a[2]));
pq.add(new int[]{0, 0, grid[0][0]});
while (!pq.isEmpty()) {
int[] curr = pq.poll();
int x = curr[0], y = curr[1], t = curr[2];
if (x == m - 1 && y == n - 1) {
return t;
}
Arrays.stream(directions)
.map(dir -> new int[]{x + dir[0], y + dir[1]})
.filter(pos -> pos[0] >= 0 && pos[0] < m && pos[1] >= 0 && pos[1] < n)
.forEach(pos -> {
int nx = pos[0], ny = pos[1];
int newTime = Math.max(t, grid[nx][ny]);
if (newTime < time[nx][ny]) {
time[nx][ny] = newTime;
pq.add(new int[]{nx, ny, newTime});
}
});
}
return -1; // If no path is found
}
}
解释
方法:
该题解使用了两个广度优先搜索(BFS)来解决问题。第一个BFS从已经被淹没的地方开始,计算每个点被淹没的时间。第二个BFS从起点开始,寻找到达终点的最短路径,同时确保在每一步行走时,该位置尚未被淹没。如果可以到达终点,则返回所需的最短时间,否则返回-1。
时间复杂度:
O(mn)
空间复杂度:
O(mn)
代码细节讲解
🦆
为什么题解中选择使用两次广度优先搜索(BFS)而不是其他算法,如深度优先搜索(DFS)或迪杰斯特拉算法?
▷🦆
题解中没有明确说明如何处理边界条件,比如起点或终点已被初始淹没的情况,这种情况下算法的输出是什么?
▷🦆
在代码实现中,变量`t`在第一个BFS和第二个BFS中有不同的作用和含义,请问这种设计有什么特别的考虑吗?
▷