Skip to content

Commit ddebd1a

Browse files
committed
feat: add solutions to lc problem: No.1254.Number of Closed Islands
1 parent ef38dc8 commit ddebd1a

File tree

6 files changed

+667
-3
lines changed

6 files changed

+667
-3
lines changed

solution/1200-1299/1254.Number of Closed Islands/README.md

Lines changed: 267 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -54,27 +54,292 @@
5454
<li><code>0 &lt;= grid[i][j] &lt;=1</code></li>
5555
</ul>
5656

57-
5857
## 解法
5958

6059
<!-- 这里可写通用的实现逻辑 -->
6160

61+
并查集。
62+
63+
并查集模板:
64+
65+
模板 1——朴素并查集:
66+
67+
```python
68+
# 初始化,p存储每个点的父节点
69+
p = list(range(n))
70+
71+
# 返回x的祖宗节点
72+
def find(x):
73+
if p[x] != x:
74+
# 路径压缩
75+
p[x] = find(p[x])
76+
return p[x]
77+
78+
# 合并a和b所在的两个集合
79+
p[find(a)] = find(b)
80+
```
81+
82+
模板 2——维护 size 的并查集:
83+
84+
```python
85+
# 初始化,p存储每个点的父节点,size只有当节点是祖宗节点时才有意义,表示祖宗节点所在集合中,点的数量
86+
p = list(range(n))
87+
size = [1] * n
88+
89+
# 返回x的祖宗节点
90+
def find(x):
91+
if p[x] != x:
92+
# 路径压缩
93+
p[x] = find(p[x])
94+
return p[x]
95+
96+
# 合并a和b所在的两个集合
97+
if find(a) != find(b):
98+
size[find(b)] += size[find(a)]
99+
p[find(a)] = find(b)
100+
```
101+
102+
模板 3——维护到祖宗节点距离的并查集:
103+
104+
```python
105+
# 初始化,p存储每个点的父节点,d[x]存储x到p[x]的距离
106+
p = list(range(n))
107+
d = [0] * n
108+
109+
# 返回x的祖宗节点
110+
def find(x):
111+
if p[x] != x:
112+
t = find(p[x])
113+
d[x] += d[p[x]]
114+
p[x] = t
115+
return p[x]
116+
117+
# 合并a和b所在的两个集合
118+
p[find(a)] = find(b)
119+
d[find(a)] = distance
120+
```
121+
122+
本题与常规并查集统计岛屿题其实差不多,不同之处在于:增加了检测岛屿是否接触边缘的操作。
123+
62124
<!-- tabs:start -->
63125

64126
### **Python3**
65127

66128
<!-- 这里可写当前语言的特殊实现逻辑 -->
67129

68130
```python
69-
131+
class Solution:
132+
def closedIsland(self, grid: List[List[int]]) -> int:
133+
m, n = len(grid), len(grid[0])
134+
p = list(range(m * n))
135+
136+
def find(x):
137+
if p[x] != x:
138+
p[x] = find(p[x])
139+
return p[x]
140+
141+
for i in range(m):
142+
for j in range(n):
143+
if grid[i][j] == 1:
144+
continue
145+
idx = i * n + j
146+
if i < m - 1 and grid[i + 1][j] == 0:
147+
p[find(idx)] = find((i + 1) * n + j)
148+
if j < n - 1 and grid[i][j + 1] == 0:
149+
p[find(idx)] = find(i * n + j + 1)
150+
151+
s = [0] * (m * n)
152+
for i in range(m):
153+
for j in range(n):
154+
if grid[i][j] == 0:
155+
s[find(i * n + j)] = 1
156+
for i in range(m):
157+
for j in range(n):
158+
root = find(i * n + j)
159+
if not s[root]:
160+
continue
161+
if i == 0 or i == m - 1 or j == 0 or j == n - 1:
162+
s[root] = 0
163+
return sum(s)
70164
```
71165

72166
### **Java**
73167

74168
<!-- 这里可写当前语言的特殊实现逻辑 -->
75169

76170
```java
171+
class Solution {
172+
private int[] p;
173+
174+
public int closedIsland(int[][] grid) {
175+
int m = grid.length, n = grid[0].length;
176+
p = new int[m * n];
177+
for (int i = 0; i < m * n; ++i) {
178+
p[i] = i;
179+
}
180+
for (int i = 0; i < m; ++i) {
181+
for (int j = 0; j < n; ++j) {
182+
if (grid[i][j] == 1) {
183+
continue;
184+
}
185+
int idx = i * n + j;
186+
if (i < m - 1 && grid[i + 1][j] == 0) {
187+
p[find(idx)] = find((i + 1) * n + j);
188+
}
189+
if (j < n - 1 && grid[i][j + 1] == 0) {
190+
p[find(idx)] = find(i * n + j + 1);
191+
}
192+
}
193+
}
194+
boolean[] s = new boolean[m * n];
195+
for (int i = 0; i < m; ++i) {
196+
for (int j = 0; j < n; ++j) {
197+
if (grid[i][j] == 0) {
198+
s[find(i * n + j)] = true;
199+
}
200+
}
201+
}
202+
for (int i = 0; i < m; ++i) {
203+
for (int j = 0; j < n; ++j) {
204+
int root = find(i * n + j);
205+
if (!s[root]) {
206+
continue;
207+
}
208+
if (i == 0 || i == m - 1 || j == 0 || j == n - 1) {
209+
s[root] = false;
210+
}
211+
}
212+
}
213+
int res = 0;
214+
for (int i = 0; i < m * n; ++i) {
215+
if (s[i]) {
216+
++res;
217+
}
218+
}
219+
return res;
220+
}
221+
222+
private int find(int x) {
223+
if (p[x] != x) {
224+
p[x] = find(p[x]);
225+
}
226+
return p[x];
227+
}
228+
}
229+
```
230+
231+
### **C++**
232+
233+
```cpp
234+
class Solution {
235+
public:
236+
vector<int> p;
237+
238+
int closedIsland(vector<vector<int>>& grid) {
239+
int m = grid.size(), n = grid[0].size();
240+
p.resize(m * n);
241+
for (int i = 0; i < m * n; ++i) p[i] = i;
242+
for (int i = 0; i < m; ++i)
243+
{
244+
for (int j = 0; j < n; ++j)
245+
{
246+
if (grid[i][j] == 1) continue;
247+
int idx = i * n + j;
248+
if (i < m - 1 && grid[i + 1][j] == 0) p[find(idx)] = find((i + 1) * n + j);
249+
if (j < n - 1 && grid[i][j + 1] == 0) p[find(idx)] = find(i * n + j + 1);
250+
}
251+
}
252+
vector<bool> s(m * n, false);
253+
for (int i = 0; i < m; ++i)
254+
{
255+
for (int j = 0; j < n; ++j)
256+
{
257+
if (grid[i][j] == 0) s[find(i * n + j)] = true;
258+
}
259+
}
260+
for (int i = 0; i < m; ++i)
261+
{
262+
for (int j = 0; j < n; ++j)
263+
{
264+
int root = find(i * n + j);
265+
if (!s[root]) continue;
266+
if (i == 0 || i == m - 1 || j == 0 || j == n - 1) s[root] = false;
267+
}
268+
}
269+
int res = 0;
270+
for (auto e : s)
271+
{
272+
if (e) ++res;
273+
}
274+
return res;
275+
}
276+
277+
int find(int x) {
278+
if (p[x] != x) p[x] = find(p[x]);
279+
return p[x];
280+
}
281+
};
282+
```
77283
284+
### **Go**
285+
286+
```go
287+
var p []int
288+
289+
func closedIsland(grid [][]int) int {
290+
m, n := len(grid), len(grid[0])
291+
p = make([]int, m*n)
292+
for i := 0; i < len(p); i++ {
293+
p[i] = i
294+
}
295+
for i := 0; i < m; i++ {
296+
for j := 0; j < n; j++ {
297+
if grid[i][j] == 1 {
298+
continue
299+
}
300+
idx := i*n + j
301+
if i < m-1 && grid[i+1][j] == 0 {
302+
p[find(idx)] = find((i+1)*n + j)
303+
}
304+
if j < n-1 && grid[i][j+1] == 0 {
305+
p[find(idx)] = find(i*n + j + 1)
306+
}
307+
}
308+
}
309+
s := make([]bool, m*n)
310+
for i := 0; i < m; i++ {
311+
for j := 0; j < n; j++ {
312+
if grid[i][j] == 0 {
313+
s[find(i*n+j)] = true
314+
}
315+
}
316+
}
317+
for i := 0; i < m; i++ {
318+
for j := 0; j < n; j++ {
319+
root := find(i*n + j)
320+
if !s[root] {
321+
continue
322+
}
323+
if i == 0 || i == m-1 || j == 0 || j == n-1 {
324+
s[root] = false
325+
}
326+
}
327+
}
328+
res := 0
329+
for _, e := range s {
330+
if e {
331+
res++
332+
}
333+
}
334+
return res
335+
}
336+
337+
func find(x int) int {
338+
if p[x] != x {
339+
p[x] = find(p[x])
340+
}
341+
return p[x]
342+
}
78343
```
79344

80345
### **...**

0 commit comments

Comments
 (0)