题目描述
You are given an n×m grid a of non-negative integers. The value ai,j represents the depth of water at the i -th row and j -th column.
A lake is a set of cells such that:
- each cell in the set has ai,j>0 , and
- there exists a path between any pair of cells in the lake by going up, down, left, or right a number of times and without stepping on a cell with ai,j=0 .
The volume of a lake is the sum of depths of all the cells in the lake.
Find the largest volume of a lake in the grid.
输入格式
The first line contains a single integer t ( 1≤t≤104 ) — the number of test cases.
The first line of each test case contains two integers n,m ( ≤n,m≤1000 ) — the number of rows and columns of the grid, respectively.
Then n lines follow each with m integers ai,j ( 0≤ai,j≤1000 ) — the depth of the water at each cell.
It is guaranteed that the sum of n⋅m over all test cases does not exceed 106106 .
输出格式
For each test case, output a single integer — the largest volume of a lake in the grid.
题意翻译
给定 n×m 的矩阵,正整数上、下、左、右相连构成一个连通块。定义一个连通块的权值为该连通块中所有数的和。求矩阵中最大的连通块。
Translated by @JYqwq
输入输出样例
输入 #1复制
5 3 3 1 2 0 3 4 0 0 0 5 1 1 0 3 3 0 1 1 1 0 1 1 1 1 5 5 1 1 1 1 1 1 0 0 0 1 1 0 5 0 1 1 0 0 0 1 1 1 1 1 1 5 5 1 1 1 1 1 1 0 0 0 1 1 1 4 0 1 1 0 0 0 1 1 1 1 1 1
输出 #1复制
10 0 7 16 21
思路:
其实就是bfs的模板题,只是在扩展时要判断你将要扩展的点是否为0,联通块问题,如果我们将要扩展的这个点为0的话,是不能扩展的,所以在判断条件上g[x][y]!=0
代码实现:
#include<bits/stdc++.h>
using namespace std;
typedef pair<int,int> PII;
const int N=1005;
int n,m;
int jump[4][4]= {{1,0},{-1,0},{0,1},{0,-1}}; // 扩展方向 上、下、左、右
int g[N][N]; // 存储图
bool vis[N][N];
int ans;
int bfs(int x,int y)
{
queue<PII>q;
q.push({x,y});
int res=g[x][y];
while(!q.empty())
{
PII t=q.front();
q.pop();
int tx=t.first;
int ty=t.second;
for(int i=0; i<4; i++)
{
int X=tx+jump[i][0];
int Y=ty+jump[i][1];
if(!vis[X][Y] && X>=1 && X<=n && Y<=m && Y>=1 && g[X][Y]!=0)
{
vis[X][Y]=true;
q.push({X,Y});
res+=g[X][Y]; //将所有联通的点的权值加起来
}
}
}
return res;
}
int main()
{
int T;
cin>>T;
while(T--)
{
ans=0;
cin>>n>>m;
for(int i=1; i<=n; i++)
{
for(int j=1; j<=m; j++)
{
cin>>g[i][j];
}
}
for(int i=1; i<=n; i++)
{
for(int j=1; j<=m; j++)
{
if(g[i][j]!=0)
{
vis[i][j]=true;
int res=bfs(i,j);
ans=max(ans,res); // 取所有连通块中的最大值
}
}
}
cout<<ans<<endl;
memset(vis,false,sizeof(vis)); // 多组数据输入输出,记得将vis 数组标记取消
}
return 0;
}