Given a 2D binary matrix filled with 0's and 1's, find the largest square containing all 1's and return its area.
For example, given the following matrix:
1 0 1 0 0 1 0 1 1 1 1 1 1 1 1 1 0 0 1 0
Return 4.
Credits:
Special thanks to @Freezen for adding this problem and creating all test cases.
这道题我刚看到的时候,马上联想到了之前的一道Number of Islands 岛屿的数量,但是仔细一对比,发现又不太一样,那道题1的形状不确定,很适合DFS的特点,而这道题要找的是正方形,是非常有特点的形状,所以并不需要用到DFS,要论相似,我到认为这道Maximal Rectangle 最大矩形更相似一些。这道题的解法不止一种,我们先来看一种brute force的方法,这种方法的机理就是就是把数组中每一个点都当成正方形的左顶点来向右下方扫描,来寻找最大正方形。具体的扫描方法是,确定了左顶点后,再往下扫的时候,正方形的竖边长度就确定了,只需要找到横边即可,这时候我们使用直方图的原理,从其累加值能反映出上面的值是否全为1,之前也有一道关于直方图的题Largest Rectangle in Histogram 直方图中最大的矩形 。通过这种方法我们就可以找出最大的正方形,参见代码如下:
解法一
class Solution { public: int maximalSquare(vector<vector<char> >& matrix) { int res = 0; for (int i = 0; i < matrix.size(); ++i) { vector<int> v(matrix[i].size(), 0); for (int j = i; j < matrix.size(); ++j) { for (int k = 0; k < matrix[j].size(); ++k) { if (matrix[j][k] == '1') ++v[k]; } res = max(res, getSquareArea(v, j - i + 1)); } } return res; } int getSquareArea(vector<int> &v, int k) { if (v.size() < k) return 0; int count = 0; for (int i = 0; i < v.size(); ++i) { if (v[i] != k) count = 0; else ++count; if (count == k) return k * k; } return 0; } };
参考资料:
https://leetcode.com/discuss/38485/my-concise-solution-in-c
https://leetcode.com/discuss/38489/easy-solution-with-detailed-explanations-8ms-time-and-space
http://www.5uzh.com/view.aspx?kn=50037263