117 lines
3.9 KiB
JavaScript
117 lines
3.9 KiB
JavaScript
/**
|
||
* @param {character[][]} grid
|
||
* @return {number}
|
||
* https://leetcode.cn/problems/number-of-islands/?envType=study-plan-v2&envId=top-interview-150
|
||
*/
|
||
const numIslands = function (grid) {
|
||
|
||
};
|
||
|
||
/*
|
||
使用深度优先遍历,在character[][]这个二维数组中,我们认为相邻的‘1’之间都有一条边,首先遍历这个二维数组,从遇到的第一个为1的位置,递归
|
||
的开始向四周查找其他位置是否也为1,如果是的话就继续寻找,并且把找过的位置设置为0,计数加一即可,先当与图中有几个连通分量
|
||
*/
|
||
|
||
function f1(grid) {
|
||
/*
|
||
递归函数向grid[r][c]四周继续递归寻找为1的位置,并把它设置成0,当整个为1位置都为0,表示整个岛屿的小时
|
||
*/
|
||
const dfs = (grid, r, c) => {
|
||
// 如果r,c超出边界,或者grid[r][c] === 0 表示岛屿的边界结束
|
||
if (r < 0 || c < 0 || r >= nr || c >= nc || grid[r][c] === '0') return;
|
||
// 将当前位置设置为0,表示已经访问过
|
||
grid[r][c] = '0';
|
||
// 递归的查找四周
|
||
dfs(grid, r - 1, c); // 上
|
||
dfs(grid, r, c + 1); // 右
|
||
dfs(grid, r + 1, c); // 下
|
||
dfs(grid, r, c - 1); // 左
|
||
};
|
||
|
||
// 如果邻接矩阵为空,或者没有任何数据,直接返回0
|
||
if (!grid || grid.length === 0) return 0;
|
||
let nr = grid.length; // 获取行的个数
|
||
let nc = grid[0].length; // 获取列的个数
|
||
let lands = 0; // 岛屿数量
|
||
|
||
for (let r = 0; r < nr; ++r) {
|
||
for (let c = 0; c < nc; ++c) {
|
||
if (grid[r][c] === '1') { // 发现陆地,必定有一座岛,把相邻的陆地全部清空
|
||
lands++;
|
||
dfs(grid, r, c); // 从当前点开始DFS
|
||
}
|
||
}
|
||
}
|
||
|
||
return lands;
|
||
}
|
||
|
||
/*
|
||
使用BFS,思路和DFS一致
|
||
*/
|
||
function f2(grid) {
|
||
// 获取网格的行数
|
||
const nr = grid.length;
|
||
if (nr === 0) return 0; // 如果网格为空,返回0岛屿
|
||
// 获取网格的列数
|
||
const nc = grid[0].length;
|
||
|
||
// 记录岛屿的数量
|
||
let num_islands = 0;
|
||
|
||
// 遍历每个格子
|
||
for (let r = 0; r < nr; r++) {
|
||
for (let c = 0; c < nc; c++) {
|
||
// 如果当前格子是陆地('1'),说明找到了一个新的岛屿
|
||
if (grid[r][c] === '1') {
|
||
// 增加岛屿数量
|
||
num_islands++;
|
||
// 将当前格子标记为已访问,防止再次访问
|
||
grid[r][c] = '0';
|
||
|
||
// 创建一个队列来进行BFS
|
||
const neighbors = [];
|
||
neighbors.push([r, c]); // 将当前岛屿的起始点入队列
|
||
|
||
// 进行BFS遍历岛屿中的所有陆地
|
||
while (neighbors.length > 0) {
|
||
// 获取队列的第一个元素
|
||
const [row, col] = neighbors.shift();
|
||
|
||
// 检查上下左右四个方向的相邻格子
|
||
// 上
|
||
if (row - 1 >= 0 && grid[row - 1][col] === '1') {
|
||
neighbors.push([row - 1, col]);
|
||
grid[row - 1][col] = '0'; // 将相邻陆地标记为水
|
||
}
|
||
// 下
|
||
if (row + 1 < nr && grid[row + 1][col] === '1') {
|
||
neighbors.push([row + 1, col]);
|
||
grid[row + 1][col] = '0'; // 将相邻陆地标记为水
|
||
}
|
||
// 左
|
||
if (col - 1 >= 0 && grid[row][col - 1] === '1') {
|
||
neighbors.push([row, col - 1]);
|
||
grid[row][col - 1] = '0'; // 将相邻陆地标记为水
|
||
}
|
||
// 右
|
||
if (col + 1 < nc && grid[row][col + 1] === '1') {
|
||
neighbors.push([row, col + 1]);
|
||
grid[row][col + 1] = '0'; // 将相邻陆地标记为水
|
||
}
|
||
}
|
||
}
|
||
}
|
||
}
|
||
|
||
// 返回岛屿的数量
|
||
return num_islands;
|
||
}
|
||
|
||
/*
|
||
利用并查集,矩阵里面所有的‘1’都认为是一个小岛屿,用一个一维数组parent表示并查集,以 grid[i][j] === '1' 这个位置为例,那么这个
|
||
位置在并查集中的下标就是parent[i*col+j] col表示矩阵的列数,而parent[i * col + j]表示的是它的父节点,默认指向自己,定义一个遍历count
|
||
记录岛屿的数量,
|
||
*/
|
||
// TODO:
|