LeetCode 2290. 到达角落需要移除障碍物的最小数目
Dijkstra
typedef array<int, 3> AI3;
class Solution {
public:
int dx[4] = {-1, 0, 1, 0}, dy[4] = {0, 1, 0, -1};
int dijkstra(vector<vector<int>>& g)
{
int n = g.size(), m = g[0].size();
vector<vector<bool>> st(n + 1, vector<bool>(m + 1, false));
priority_queue<AI3, vector<AI3>, greater<AI3>> heap;
heap.push({0, 0, 0});
while(heap.size())
{
auto [c, x, y] = heap.top(); //注意不能取引用
heap.pop();
if(st[x][y]) continue;
if(x == n - 1 && y == m - 1) return c;
st[x][y] = true;
for(int i = 0; i < 4; i ++)
{
int a = x + dx[i], b = y + dy[i];
if(a < 0 || a >= n || b < 0 || b >= m || st[a][b]) continue;
heap.push({c + g[a][b], a, b});
}
}
return -1;
}
int minimumObstacles(vector<vector<int>>& g) {
return dijkstra(g);
}
};
0 - 1 BFS 优化
const int INF = 0x3f3f3f;
typedef pair<int, int> PII;
class Solution {
public:
int dx[4] = {-1, 0, 1, 0}, dy[4] = {0, 1, 0, -1};
int get(int x, int M)
{
return (x + M) % M;
}
int bfs(vector<vector<int>>& g)
{
int n = g.size(), m = g[0].size();
vector<vector<bool>> st(n + 1, vector<bool>(m + 1, false));
vector<vector<int>> dist(n + 1, vector<int>(m + 1, INF));
PII q[n * m + 10]; int hh = 0, tt = 0;
dist[0][0] = 0;
q[tt ++] = {0, 0};
while(hh != tt)
{
auto [x, y] = q[hh];
hh = get(hh + 1, n * m);
if(st[x][y]) continue;
if(x == n - 1 && y == m - 1) return dist[x][y];
st[x][y] = true;
for(int i = 0; i < 4; i ++)
{
int a = x + dx[i], b = y + dy[i];
if(a < 0 || a >= n || b < 0 || b >= m || st[a][b]) continue;
if(dist[a][b] < dist[x][y] + g[a][b]) continue;
if(g[a][b])
q[tt] = {a, b}, tt = get(tt + 1, n * m), dist[a][b] = dist[x][y] + 1;
else
hh = get(hh - 1, n * m), q[hh] = {a, b}, dist[a][b] = dist[x][y];
}
}
return -1;
}
int minimumObstacles(vector<vector<int>>& grid) {
return bfs(grid);
}
};