题目链接:Islands HDU - 2808
===================================================
Islands
Time Limit: 1000 ms
Memory Limit: 32768 kB
Description
There are so many islands in the sea. Some islands are enclosed by other ones. So, we can classify all the islands to several levels. An island has a level of 0 if it is contains no other islands. An island has a level of K+1 if it contains one or more islands and the highest level of the contained island(s) is K. Now, the map of the sea is given. Your task is to calculate the areas of islands in each level.
Input
The input contains several test cases. Each test case starts with a line contains two numbers N and M(1<=N<=100,1<=M<=100) which indicate the size of the map. The next N lines will contain M characters each to represent the map. Each character is either ‘x’ or ‘.’. A sea is defined as a maximal connected group of ‘.’ cells, where two ‘.’ cells are connected if they are vertically or horizontally adjacent. An island is defined as a maximal connected group of ‘x’ cells, where two ‘x’ cells are connected if they are vertically, horizontally, or diagonally adjacent. An island A contains island B if A and B are different and if you start sailing from any point of island B, you won’t be able to sail out of island A.
Output
For each test case, output a single line with K+1 integers, where K is the highest level of an island in the map. The i-th number in the line is the total area of islands of level (i-1).
Sample Input
1 1
x
5 7
.xxxxx.
x…x
x.x.x.x
x…x
.xxxxx.
Sample Output
1
2 16
===================================================
题意:就是100*100的地图,上面有海和岛,岛是8各方向判断是否连接的,然后如果一座岛里面没有其他岛的话,他的岛等级就是0,如果存在其他岛的话,他的等级就是他的子岛最大等级+1.
算法:DFS
思路:
- 这题和前面那道埃及文字题目差不多,Ancient Messages HDU - 3839。
- 就是从边缘开始判断,海的话就进行dfs判断,把所有外海标记了,然后与外海邻接的岛就记录;然后在从这些岛开始dfs判断,一座岛一座岛标记,然后每次都把与这些岛邻接的内海进行记录,再对这些内海进行标记,反正就是互相套娃。
- 当一座岛里面没有海或者内海里面没有外岛,他的等级就是0了。
易错点:注意细节,耐心耐心耐心
===================================================
#include <iostream>
#include <vector>
#include <cstring>
#include <algorithm>
#include <queue>
#include <cstdio>
#include <map>
using namespace std;
const int INF = 0x3f3f3f3f;
char ditu[100][100];
bool vis[100][100];
bool visB[100][100];
bool visW[100][100];
int n,m;
int xx[]={1,-1,0,0,-1,-1,1,1};
int yy[]={0,0,1,-1,-1,1,1,-1};
int ans[100],ansN;
void show(){
for(int i=0;i<n;i++){
for(int j=0;j<m;j++) cout<<ditu[i][j];cout<<endl;
}cout<<endl;
}
void init(){
for(int i=0;i<n;i++) cin>>ditu[i];
memset(vis,false,sizeof vis);
memset(visB,false,sizeof visB);
memset(visW,false,sizeof visW);
memset(ans,0,sizeof ans);
ansN = -1;
}
struct node{
int x,y;
node(int a,int b):x(a),y(b) {};
};
void show2(vector<node> a){
cout<<"vector: ";
for(int i=0;i<a.size();i++){
cout<<a[i].x<<" "<<a[i].y<<" | ";
}cout<<endl;
}
void show3(){
for(int i=0;i<n;i++){
for(int j=0;j<m;j++) cout<<vis[i][j]<<" ";cout<<endl;
}cout<<endl;
}
void cleanW(int a,int b,vector<node> &v){
vis[a][b]=true;
for(int i=0;i<4;i++){
int x = a + xx[i] , y = b+ yy[i];
if(x<0||x>=n||y<0||y>=m||vis[x][y]) continue;
if(ditu[x][y]=='.') cleanW(x,y,v);
else if(!visB[x][y]) visB[x][y] = true,v.push_back(node(x,y));
}
}
void cleanB(int a,int b,vector<node> &v,int &c){
vis[a][b]=true;c++;
for(int i=0;i<8;i++){
int x = a + xx[i] , y = b+ yy[i];
if(x<0||x>=n||y<0||y>=m||vis[x][y]) continue;
if(ditu[x][y]=='x') cleanB(x,y,v,c);
else if(!visW[x][y]) visW[x][y] = true,v.push_back(node(x,y));
}
}
int dfs(int x,int y) {
vector<node> v,v2;
int res = 0;
int level = 0;
cleanB(x,y,v,res);
if(v.size()==0) {ans[0]+=res;return 0;}
//show2(v);show3();
for(int i=0;i<v.size();i++){
int a = v[i].x , b = v[i].y;
if(vis[a][b]) continue;
cleanW(a,b,v2);
}
// show2(v2);show3();
if(v2.size()==0) {ans[0]+=res;return 0;}
for(int i=0;i<v2.size();i++){
int a = v2[i].x , b = v2[i].y;
if(vis[a][b]) continue;
level = max(level,dfs(a,b)+1);
}
ans[level]+=res;
return level;
};
void solve(){
vector<node> v;
for(int i=0;i<n;i++){
if(!vis[i][0]){
if(ditu[i][0]=='.') cleanW(i,0,v);
else if(!visB[i][0]) visB[i][0] = true,v.push_back(node(i,0));
}
if(!vis[i][m-1]){
if(ditu[i][m-1]=='.') cleanW(i,m-1,v);
else if(!visB[i][m-1]) visB[i][m-1] = true,v.push_back(node(i,m-1));
}
}
for(int j=1;j<m-1;j++){
if(!vis[0][j]){
if(ditu[0][j]=='.') cleanW(0,j,v);
else if(!visB[0][j]) visB[0][j] = true,v.push_back(node(0,j));
}
if(!vis[n-1][j]){
if(ditu[n-1][j]=='.') cleanW(n-1,j,v);
else if(!visB[n-1][j]) visB[n-1][j] = true,v.push_back(node(n-1,j));
}
}
//------------------------------------------------------------------------------------
//show2(v);show3();
for(int i=0;i<v.size();i++){
int a = v[i].x , b = v[i].y;
if(vis[a][b]) continue;
ansN = max(ansN,dfs(a,b));
}
}
int main()
{
while(cin>>n>>m){
init();//show();
solve();
//cout<<ansN<<endl;
if(ansN==-1) {cout<<endl;continue;}
for(int i=0;i<ansN;i++) cout<<ans[i]<<" ";cout<<ans[ansN]<<endl;
}
return 0;
}