302. Smallest Rectangle Enclosing Black Pixels (题目链接)
Hard
An image is represented by a binary matrix with 0
as a white pixel and 1
as a black pixel. The black pixels are connected, i.e., there is only one black region. Pixels are connected horizontally and vertically. Given the location (x, y)
of one of the black pixels, return the area of the smallest (axis-aligned) rectangle that encloses all black pixels.
Example:
Input:
[
"0010",
"0110",
"0100"
]
and x = 0,
y = 2
Output: 6
方法1:暴力 (O(n))
直接遍历所有的位置,统计出上下左右的最大边界
class Solution:
def minArea(self, image: List[List[str]], x: int, y: int) -> int:
col = len(image[0])
row = len(image)
left, right, top, down = float('inf'), -1, float('inf'), -1
for i in range(row):
for j in range(col):
if image[i][j] == '1':
left = min(left, j)
right = max(right, j)
top = min(top, i)
down = max(down, i)
return (right - left + 1) * (down - top + 1)
方法2:二分法(log m + log n)m为行,n为列
参考 https://www.cnblogs.com/grandyang/p/5268775.html
class Solution:
def searchTop(self, t, d, l, r, image):
while t < d:
m = (t + d) // 2
start = l
while start <= r and image[m][start] == '0':
start += 1
if start <= r:
d = m
else:
t = m + 1
return t
def searchDown(self, t, d, l, r, image):
while t < d:
m = (t + d + 1) // 2
start = l
while start <= r and image[m][start] == '0':
start += 1
if start <= r:
t = m
else:
d = m - 1
return t
def searchLeft(self, t, d, l, r, image):
while l < r:
m = (l + r) // 2
start = t
while start <= d and image[start][m] == '0':
start += 1
if start <= d:
r = m
else:
l = m + 1
return l
def searchRight(self, t, d, l, r, image):
while l < r:
m = (l + r + 1) // 2
start = t
while start <= d and image[start][m] == '0':
start += 1
if start <= d:
l = m
else:
r = m - 1
return l
def minArea(self, image: List[List[str]], x: int, y: int) -> int:
col, row = len(image[0]) - 1, len(image) - 1
top = self.searchTop(0, x, 0, col, image)
down = self.searchDown(x, row, 0, col, image)
left = self.searchLeft(top, down, 0, y, image)
right = self.searchRight(top, down, y, col, image)
return (right - left + 1) * (down - top + 1)