来源:力扣(LeetCode)
链接:https://leetcode-cn.com/problems/number-of-islands
题目描述:
给你一个由 '1'(陆地)和 '0'(水)组成的的二维网格,请你计算网格中岛屿的数量。
岛屿总是被水包围,并且每座岛屿只能由水平方向或竖直方向上相邻的陆地连接形成。
此外,你可以假设该网格的四条边均被水包围。
示例 1:
输入:
[
['1','1','1','1','0'],
['1','1','0','1','0'],
['1','1','0','0','0'],
['0','0','0','0','0']
]
输出: 1
示例 2:
输入:
[
['1','1','0','0','0'],
['1','1','0','0','0'],
['0','0','1','0','0'],
['0','0','0','1','1']
]
输出: 3
解释: 每座岛屿只能由水平和/或竖直方向上相邻的陆地连接而成。
写法1:
int numIslands(vector<vector<char>>& grid) {
int Height = grid.size();
if (Height <= 0)
return -1;
int width = grid[0].size();
unordered_set <pair<int,int>>used_party;
int num_party(0);//岛屿的数量
for (size_t r = 0; r < width; r++)
{
for (size_t c = 0; c < Height; c++)
{
if (grid[r][c] == '1')
{
num_party++; //岛屿数量加1
grid[r][c] = '0';
queue<pair<int, int>> neighbors;
used_party.insert({0,0});
neighbors.push(pair<int, int>(r, c));
while (!neighbors.empty())
{
auto ptr_party = neighbors.front();
neighbors.pop();
int now_r = ptr_party.first;
int now_c = ptr_party.second;
if ((now_r - 1 >= 0) && (grid[now_r - 1][now_c] == '1'))
{
grid[now_r - 1][now_c] = '0';
neighbors.push(pair<int, int>(now_r - 1, now_c));
}
if ((now_r + 1 < width) && (grid[now_r + 1][now_c] == '1'))
{
grid[now_r + 1][now_c] = '0';
neighbors.push(pair<int, int>(now_r + 1, now_c));
}
if ((now_c - 1 >= 0) && (grid[now_r][now_c - 1] == '1'))
{
grid[now_r][now_c - 1] = '0';
neighbors.push(pair<int, int>(now_r, now_c - 1));
}
if ((now_c + 1 < Height) && (grid[now_r][now_c + 1] == '1'))
{
grid[now_r][now_c + 1] = '0';
neighbors.push(pair<int, int>(now_r, now_c + 1));
}
}
}
}
}
return num_party;
}
然后再看到了大神的关于广度优先搜索的框架之后,想试一下,就改写了一下;
我的理解就是,需要建立一个容器来存放节点,可以是队列,然后从队列开始,在其周围的邻域进行收缩,符合标准的加入队列,在下一次循环式作为节点进行搜索。
除此之外还必须有一个专门存放使用过(搜索过的)节点的标志信息,避免重复进行搜索。
//本程序是对照leetcode 找到岛屿而写的
#include<cstdio>
#include<cstring>
#include<algorithm>
#include<iostream>
#include<string>
#include<vector>
#include<queue>
#include <unordered_set>
using namespace std;
class Solution {
public:
string trans_pairInt2string(int row, int colun){
//为了进行存放使用过的节点信息,用string拼接进行标志位的存放
string str = "";
string res = str + to_string(row);
res = res + ',';
res = res + to_string(colun);
return res;
}
int numIslands(vector<vector<char>>& grid) {
int Height = grid.size();
if (Height <= 0)
return -1;
int width = grid[0].size();
unordered_set <string>used_party;//使用过的节点
int num_party(0);//岛屿的数量
for (int r = 0; r < width; r++)
{
for (int c = 0; c < Height; c++)
{
if (grid[r][c] == '1')
{
//cout << used_party.count(trans_pairInt2string(r, c)) << endl;
if (used_party.count(trans_pairInt2string(r,c))<=0)
{
num_party++; //岛屿数量加1
used_party.insert(trans_pairInt2string(r, c));
}
queue<pair<int, int>> neighbors;
neighbors.push(pair<int, int>(r, c));
while (!neighbors.empty())
{
auto ptr_party = neighbors.front();
neighbors.pop();
int now_r = ptr_party.first;
int now_c = ptr_party.second;
if ((now_r - 1 >= 0) && (grid[now_r - 1][now_c] == '1'))
{
if (used_party.count(trans_pairInt2string(now_r-1, now_c))<=0)
{
neighbors.push(pair<int, int>(now_r - 1, now_c));
used_party.insert(trans_pairInt2string(now_r - 1, now_c));
}
}
if ((now_r + 1 < width) && (grid[now_r + 1][now_c] == '1'))
{
if (used_party.count(trans_pairInt2string(now_r + 1, now_c))<=0)
{
neighbors.push(pair<int, int>(now_r +1, now_c));
used_party.insert(trans_pairInt2string(now_r + 1, now_c));
}
}
if ((now_c - 1 >= 0) && (grid[now_r][now_c - 1] == '1'))
{
if (used_party.count(trans_pairInt2string(now_r, now_c - 1))<=0)
{
neighbors.push(pair<int, int>(now_r, now_c - 1));
used_party.insert(trans_pairInt2string(now_r, now_c - 1));
}
}
if ((now_c + 1 < Height) && (grid[now_r][now_c + 1] == '1'))
{
if (used_party.count(trans_pairInt2string(now_r, now_c + 1))<=0)
{
neighbors.push(pair<int, int>(now_r, now_c + 1));
used_party.insert(trans_pairInt2string(now_r, now_c + 1));
}
}
}
}
}
}
return num_party;
}
};
int main() {
vector<vector<char>> party_in(4, vector<char>(4, '0'));
char A[4][4] = { { '1', '1', '0', '1'},
{ '1', '0', '0', '1'},
{ '1', '0', '0', '0'},
{ '1', '0', '0', '1'},
};
for (size_t i = 0; i < 4; i++)
{
for (size_t j = 0; j < 4; j++)
{
party_in[i][j] = A[i][j];
}
}
Solution s1;
int num_find = s1.numIslands(party_in);
cout << num_find << endl;
std::system("pause");
return 0;
}
总结:只是为了进行套用大框架,没有进行优化