题目 在一个 n×m 的方格地图上,某些方格上放置着炸弹。手动引爆一个炸弹以后,炸弹会把炸弹所在的行和列上的所有炸弹引爆,被引爆的炸弹又能引爆其他炸弹,这样连锁下去。
现在为了引爆地图上的所有炸弹,需要手动引爆其中一些炸弹,为了把危险程度降到最低,请算出最少手动引爆多少个炸弹可以把地图上的所有炸弹引爆。 输入格式 第一行输两个整数 n, m,用空格隔开。 接下来 n 行,每行输入一个长度为 m 的字符串,表示地图信息。0表示没有炸弹,1表示炸弹。 数据约定: 对于60% 的数据: 1≤n,m≤100; 对于 100% 的数据: 1≤n,m≤1000; 数据量比较大,不建议用cin输入。 输出格式 输出一个整数,表示最少需要手动引爆的炸弹数。
思路:将所以的炸弹放入一个数组中,然后对其中一个炸弹用dfs()进行连锁引爆,判断是否有还有未被引爆的,如果存在,这引爆数目加一,把当前的引爆,一直这样判断下去。
#include<iostream>
#include<vector>
using namespace std;
struct Point{
int x;
int y;
int bo;//是否引爆
};
int n,m,x = 0;
Point p[100];//存放炸弹
void DFS(Point boom,int k)
{
for(int i = 0;i < x; i++)
{
if(i!=k&&p[i].bo==1&&(boom.x==p[i].x||boom.y==p[i].y))
//如果未被引爆且行数或者列数等于其中的一个炸弹
{
p[i].bo = 0;//设置为已经爆炸了
DFS(p[i],i);
}
}
}
int main()
{
cin >> n >> m;
int num = 0;
for(int i = 0; i < n; i++)
{
for(int j = 0; j < m; j++)
{
int tmp;
scanf("%1d",&tmp);
if(tmp)
{
p[x].x = i;
p[x].y = j;
p[x].bo = 1;
x++;
}
}
}
for(int i = 0; i < x; i++)
{
if(p[i].bo)
{
num++;//需要引爆数目加一
DFS(p[i],i);
}
}
cout << num;
return 0;
}