您的位置:首页 > 其它

最大正方形

2016-06-21 16:07 176 查看
题目描述:在一个二维01矩阵中找到全为1的最大正方形

样例:

1 0 1 0 0

1 0 1 1 1

1 1 1 1 1

1 0 0 1 0

返回 4

求的是正方形的面积,当然,如果能知道这个正方形的边长就解决了。还是动态规划,用一个二维表格record记录运算结果,其中,record[i][j]表示源矩阵当中以第 i 行,第 j 列的元素为正方形右下角的最大正方形的边长。拿样例来说,record[2][3] = 2,而record[3][4] = 0,因为源矩阵这个位置是0. 那么什么时候record记录的值的大小会增加呢?

假设现在record[i - 1][j - 1]记录了以源矩阵中第 i - 1 行,第 j - 1 列的元素为正方形右下角的最大正方形的边长,那么record[i][j]的值就和matrix[i][j]所在的行和列有关系了。显然,沿着行(或列)的方向向左(或向上)追溯,看matrix中的元素的值是否都为1就成为这个最大正方形的边长是否能增加的唯一原因。但是这件事情单独做一遍效率实在太低,也没那个必要,既然record的每个元素记录的都是以这个元素为右下角的最大正方形边长,我们就可以通过这个边长来判断matrix[i][j]所在的行和列的,往上或往左回溯的,元素为"1"的个数。

写出状态转移方程:record[i][j] = min(record[i - 1][j], record[i][j - 1], record[i - 1][j - 1]) + 1

代码如下:

class Solution:
#param matrix: a matrix of 0 and 1
#return: an integer
def maxSquare(self, matrix):
m = len(matrix)
if m == 0:
return 0
n = len(matrix[0])
record = [[0 for j in range(n)] for i in range(m)]
# 对于第1行,第1列,当然元素是1的,以它为右下角的正方形边长就是1
for j in range(n):
if matrix[0][j] == 1:
record[0][j] = 1
for i in range(m):
if matrix[i][0] == 1:
record[i][0] = 1
i = 1
result = 0
while i < m:
j = 1
while j < n:
# 这个值是1,才有分析的必要,否则肯定是0
if matrix[i][j] == 1:
record[i][j] = min(record[i - 1][j - 1], record[i - 1][j], record[i][j - 1]) + 1
j += 1
result = max(result, max(record[i]))
i += 1
# result计算的是边长,而需要返回的是面积
return pow(result, 2)
# write your code here
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签:  动态规划