在给定的二维二进制数组 A
中,存在两座岛。(岛是由四面相连的 1
形成的一个最大组。)
现在,我们可以将 0
变为 1
,以使两座岛连接起来,变成一座岛。
返回必须翻转的 0
的最小数目。(可以保证答案至少是 1。)
示例 1:
输入:[[0,1],[1,0]]
输出:1
示例 2:
输入:[[0,1,0],[0,0,0],[0,0,1]]
输出:2
示例 3:
输入:[[1,1,1,1,1],[1,0,0,0,1],[1,0,1,0,1],[1,0,0,0,1],[1,1,1,1,1]]
输出:1
提示:
1 <= A.length = A[0].length <= 100
A[i][j] == 0
或 A[i][j] == 1
思路:首先利用dfs找到其中一个岛屿的全部坐标,并将这座岛的所有元素都标记为2;我们要求的就是标记为2的坐标与标记为1的坐标的最小距离;暴力法也能过,可能是测试用例太少了;我们可以利用994题腐烂橘子的思想,每次将所有腐烂的橘子向四周扩一圈,直到腐烂的橘子四周存在元素为1的坐标,即可得到最短的距离。
C++
class Solution {
public:
void dfs(vector<vector<int>>& A, vector<pair<int,int>>& tmp, int r, int c)
{
if(r-1>=0 && 1==A[r-1][c])
{
A[r-1][c]=2;
tmp.push_back(make_pair(r-1,c));
dfs(A,tmp,r-1,c);
}
if(r+1<A.size() && 1==A[r+1][c])
{
A[r+1][c]=2;
tmp.push_back(make_pair(r+1,c));
dfs(A,tmp,r+1,c);
}
if(c-1>=0 && 1==A[r][c-1])
{
A[r][c-1]=2;
tmp.push_back(make_pair(r,c-1));
dfs(A,tmp,r,c-1);
}
if(c+1<A[0].size() && 1==A[r][c+1])
{
A[r][c+1]=2;
tmp.push_back(make_pair(r,c+1));
dfs(A,tmp,r,c+1);
}
}
int shortestBridge(vector<vector<int>>& A)
{
int m=A.size();
int n=A[0].size();
int flag=0;
vector<pair<int,int>> tmp;
int res=0;
for(int i=0;i<m;i++)
{
if(flag)
{
break;
}
for(int j=0;j<n;j++)
{
if(1==A[i][j])
{
tmp.push_back(make_pair(i,j));
A[i][j]=2;
dfs(A,tmp,i,j);
flag=1;
break;
}
}
}
while(flag)
{
vector<pair<int,int>> vec;
for(auto it:tmp)
{
int r=it.first;
int c=it.second;
if(r-1>=0)
{
if(1==A[r-1][c])
{
flag=0;
break;
}
else if(0==A[r-1][c])
{
A[r-1][c]=2;
vec.push_back(make_pair(r-1,c));
}
}
if(r+1<A.size())
{
if(1==A[r+1][c])
{
flag=0;
break;
}
else if(0==A[r+1][c])
{
A[r+1][c]=2;
vec.push_back(make_pair(r+1,c));
}
}
if(c-1>=0)
{
if(1==A[r][c-1])
{
flag=0;
break;
}
else if(0==A[r][c-1])
{
A[r][c-1]=2;
vec.push_back(make_pair(r,c-1));
}
}
if(c+1<A[0].size())
{
if(1==A[r][c+1])
{
flag=0;
break;
}
else if(0==A[r][c+1])
{
A[r][c+1]=2;
vec.push_back(make_pair(r,c+1));
}
}
}
if(flag)
{
res++;
}
tmp=vec;
}
return res;
}
};
python
ort=[[0,1],[0,-1],[1,0],[-1,0]]
class Solution:
def dfs(self,A,tmp,r,c):
for it in ort:
i=r+it[0]
j=c+it[1]
if i>=0 and i<len(A) and j>=0 and j<len(A[0]) and 1==A[i][j]:
tmp.append([i,j])
A[i][j]=2
tmp=self.dfs(A,tmp,i,j)
return tmp
def shortestBridge(self, A: List[List[int]]) -> int:
m=len(A)
n=len(A[0])
flag=0
tmp=[]
for i in range(m):
if flag:
break
for j in range(n):
if 1==A[i][j]:
tmp.append([i,j])
A[i][j]=2
flag=1
tmp=self.dfs(A,tmp,i,j)
break
res=0
flag=1
while flag:
vec=[]
for it in tmp:
for ot in ort:
r=it[0]+ot[0]
c=it[1]+ot[1]
if r>=0 and r<m and c>=0 and c<n:
if 1==A[r][c]:
flag=0
break
elif 0==A[r][c]:
vec.append([r,c])
A[r][c]=2
if flag:
res+=1
tmp=vec
return res