Leetcode 827. 最大人工岛
题目
在二维地图上, 0代表海洋, 1代表陆地,我们最多只能将一格 0 海洋变成 1变成陆地。
进行填海之后,地图上最大的岛屿面积是多少?(上、下、左、右四个方向相连的 1 可形成岛屿)
测试样例
示例 1:
输入: [[1, 0], [0, 1]]
输出: 3
解释: 将一格0变成1,最终连通两个小岛得到面积为 3 的岛屿。
示例 2:
输入: [[1, 1], [1, 0]]
输出: 4
解释: 将一格0变成1,岛屿的面积扩大为 4。
示例 3:
输入: [[1, 1], [1, 1]]
输出: 4
解释: 没有0可以让我们变成1,面积依然为 4。
说明:
- 1 <= grid.length = grid[0].length <= 50
- 0 <= grid[i][j] <= 1
题解
并查集
我们先将相连的陆地加到同一个集合中,这样我们能得到多个集合。然后,我们遍历海洋,我们将其变成陆地,我们加上周围相连陆地所在集合的元素个数便是新岛的面积,这里需要注意一点,同一个集合只会计算一次,我们需要用一个set集合记录,避免重复计算。详细过程见代码
代码
class UF{
public:
vector<int> parent;
vector<int> size;
UF(int n){
parent = vector<int>(n,0);
size = vector<int>(n,1);
for(int i=0; i<n; i++)
parent[i] = i;
}
int find(int x){
while(x != parent[x]){
x = parent[x];
}
return x;
}
void Union(int x,int y){
int pX = find(x);
int pY = find(y);
if(pX == pY) return;
if(size[pX] > size[pY]){
parent[pY] = pX;
size[pX] += size[pY];
}else{
parent[pX] = pY;
size[pY] += size[pX];
}
}
int getSize(int x){
return size[find(x)];
}
};
class Solution {
public:
int largestIsland(vector<vector<int>>& grid) {
int m = grid.size(),n = grid[0].size();
int ans = 0;
UF uf = UF(m*n);
for(int i=0; i<m; i++){
for(int j=0; j<n; j++){
if(grid[i][j] == 1){
if(i-1>=0 && grid[i-1][j]==1){
uf.Union(i*n+j,(i-1)*n+j);
}
if(j-1>=0 && grid[i][j-1]==1){
uf.Union(i*n+j,i*n+j-1);
}
ans = max(ans,uf.getSize(i*n+j));
}
}
}
int dir[4][2] = { {1,0},{0,-1},{-1,0},{0,1}};
set<int> visit;
for(int i=0; i<m; i++){
for(int j=0; j<n; j++){
if(grid[i][j] == 0){
int now = 1;
for(int k=0; k<4; k++){
if(i+dir[k][0]>=0 && i+dir[k][0]<m && j+dir[k][1]>=0 && j+dir[k][1]<n){
if(grid[i+dir[k][0]][j+dir[k][1]] == 1){
int parent = uf.find((i+dir[k][0])*n+j+dir[k][1]);
if(visit.find(parent) == visit.end()){
visit.insert(parent);
now += uf.getSize(parent);
}
}
}
}
visit.clear();
ans = max(ans,now);
}
}
}
return ans;
}
};
来源:力扣(LeetCode)
链接:https://leetcode-cn.com/problems/making-a-large-island
著作权归领扣网络所有。商业转载请联系官方授权,非商业转载请注明出处。