题解【洛谷P1596】[USACO10OCT]Lake Counting

题面

( ext{Flood Fill}) 模板题。

( ext{Flood Fill}) 可以快速求出一个图中连通块的个数。

大概就是遍历每一个点,如果它没有被遍历过且是一个新连通块,那么就将答案 (+1),然后从这个点向四周扩展。

主要使用 ( ext{BFS}) 实现。

由于每个点都只会被遍历 (1) 次,因此时间复杂度是 (O(n imes m))

#include <bits/stdc++.h>

using namespace std;

const int N = 103;

int n, m, ans, cnt;
bool st[N][N];
char s[N][N];
queue <pair <int, int> > q;

inline void bfs(int x, int y)
{
    q.push(make_pair(x, y));
    st[x][y] = true;
    while (!q.empty())
    {
        pair <int, int> u = q.front(); q.pop();
        for (int i = u.first - 1; i <= u.first + 1; i+=1)
            for (int j = u.second - 1; j <= u.second + 1; j+=1)
            {
                if (i == u.first && j == u.second) continue;
                if (st[i][j] || s[i][j] != 'W') continue; //不能扩展
                st[i][j] = true; //标记已遍历
                q.push(make_pair(i, j)); //加入队列中继续扩展
            }
    }
}

int main()
{
    cin >> n >> m;
    for (int i = 1; i <= n; i+=1)
        scanf("%s", s[i] + 1);
    for (int i = 1; i <= n; i+=1)
        for (int j = 1; j <= m; j+=1)
            if (s[i][j] == 'W' && !st[i][j]) //新连通块
            {
                ++cnt; //连通块个数 +1
                bfs(i, j); //进行扩展
            }
    cout << cnt << endl;
    return 0;
}
原文地址:https://www.cnblogs.com/xsl19/p/12367262.html