hiho一下[156周]:岛屿

来源:互联网 发布:沉迷网络的危害小短文 编辑:程序博客网 时间:2024/05/17 03:04

给你一张某一海域卫星照片,你需要统计:

  1. 照片中海岛的数目

  2. 照片中面积不同的海岛数目

  3. 照片中形状不同的海岛数目

其中海域的照片如下,”.”表示海洋,”#”表示陆地。在”上下左右”四个方向上连在一起的一片陆地组成一座岛屿。

.####..  .....#.  ####.#.  .....#.  ..##.#.  

上图所示的照片中一共有4座岛屿;其中3座面积为4,一座面积为2,所以不同面积的岛屿数目是2;有两座形状都是”####”,所以形状不同的岛屿数目为3。

输入
第一行包含两个整数:N 和 M,(1 ≤ N, M ≤ 50),表示照片的行数和列数。

以下一个 N * M 的矩阵,表示表示海域的照片。

输出
输出3个整数,依次是照片中海岛的数目、面积不同的海岛数目和形状不同的海岛数目。

样例输入

5 7.####..  .....#.  ####.#.  .....#.  ..##.#.  样例输出4 2 3

思路很简单,直接dfs即可,不过,需要在搜索的过程中,记录#的数量,来表示面积,记录遍历路径,使用相对位置表示形状。

参考代码(很长,很乱,仅供参考,不建议复制粘贴):

#include <iostream>#include <string>#include <vector>#include <algorithm>#include <set>#include <map>struct point {//用一个结构体的表示路径中的点,方便记录岛屿的形状    int x;    int y;    point(int m, int n) {        x = m;        y = n;    }};struct mycomp//形状set kind的自动以排序函数{    bool operator () (const std::vector<point>& a, const std::vector<point>& b) const    {        if (a.size() == b.size()) {            for (int i = 0; i < a.size(); i++) {                if (a[i].x == b[i].x) {                    if (a[i].y == b[i].y) {                        continue;                    }                    return a[i].y > b[i].y;                }                return a[i].x > b[i].x;            }            return false;        }        return a.size() > b.size();    }};void dfs(int i, int j, std::vector<std::vector<bool> > &visited, std::vector<std::vector<char> > &grid, int &area, std::vector<point> &points) {//dfs主要实现函数    int n = grid.size();    int m = grid[0].size();    if (i < 0 || i >= n)        return;    if (j < 0 || j >= m)        return;    if (visited[i][j] || grid[i][j] == '.')        return;    visited[i][j] = true;    point p(i, j);    points.push_back(p);    area++;    dfs(i - 1, j, visited, grid, area, points);    dfs(i + 1, j, visited, grid, area, points);    dfs(i, j - 1, visited, grid, area, points);    dfs(i, j + 1, visited, grid, area, points);}int main() {    using namespace std;    int n, m;    while (cin >> n >> m) {        vector<vector<char> > grid(n, vector<char>(m));        vector<vector<bool> > visited(n, vector<bool>(m, false));        int islandNums = 0;        set<int> areas;//面积集合,表示不同面积的岛屿个数        set<vector<point>, mycomp > kinds;//形状集合,表示不同形状的岛屿个数        int area = 0;        for (int i = 0; i < n; i++) {            for (int j = 0; j < m; j++) {                cin >> grid[i][j];            }        }        for (int i = 0; i < n; i++) {            for (int j = 0; j < m; j++) {                if (grid[i][j] == '#' && !visited[i][j]) {                    vector<point> points;                    dfs(i, j, visited, grid, area, points);                    islandNums++;                    areas.insert(area);                    area = 0;                    for (int k = points.size() - 1; k >= 0; k--) {                        points[k].x -= points[0].x;                        points[k].y -= points[0].y;                    }                    kinds.insert(points);                }            }        }        cout << islandNums << " " << areas.size() << " " << kinds.size() << endl;    }    return 0;}
原创粉丝点击