LeetCode Online Judge 题目C# 练习 - Maximal Rectangle

Given a 2D matrix fill with 0's and 1's, find the largest rectangle containing all ones and return its area.

 1         public static int MaximalRectangle(List<List<char>> matrix)
 2         {
 3             int n = matrix.Count;
 4             int m = matrix[0].Count;
 5             int curr_area = 0;
 6             int max_area = 0;
 7 
 8             for (int i = 0; i < n; i++)
 9             {
10                 for (int j = 0; j < m; j++)
11                 {
12                     if(matrix[i][j] == '1')
13                     {
14                         int lastj = m;
15                         for (int k = i; k < n && matrix[k][j] == '1'; k++)
16                         {
17                             for (int l = j; l < lastj; l++)
18                             {
19                                 if (matrix[k][l] == '1')
20                                 {
21                                     curr_area = (l - j + 1) * (k - i + 1);
22                                     max_area = Math.Max(max_area, curr_area);
23                                 }
24                                 else
25                                     lastj = l;
26                             }
27                         }
28                     }
29                 }
30             }
31 
32             return max_area;
33         }

代码分析:

  Brute Force, O(n4). 每一个是1的格子,都从上至下,从左往右,去看最大面积。lastj变量是存放最小的列。

  例如:  

1 1 0 1
1 0 1 1
1 1 1 1
0 0 1 1

  [0,0] :  第一行: curr_area: 2, max_area: 2, lastj = 2

      第二行: curr_area: 2, max_area: 2, lastj = 1

      第三行: curr_area: 3, max_area: 3, lastj = 1

      max_area = 3;

  ...

 

 1         public static int MaximalRectangleOpt(List<List<char>> matrix)
 2         {
 3             int n = matrix.Count;
 4             int m = matrix[0].Count;
 5             int[,] dp = new int[n, m];
 6             int curr_area = 0;
 7             int max_area = 0;
 8             
 9             for (int i = 0; i < n; i++)
10             {
11                 for (int j = 0; j < m; j++)
12                 {
13                     if (matrix[i][j] == '1')
14                         dp[i, j] = j > 0 ? dp[i, j - 1] + 1 : 1;
15                     else
16                         dp[i, j] = 0;
17                 }
18             }
19 
20             for (int i = 0; i < n; i++)
21             {
22                 for (int j = 0; j < m; j++)
23                 {
24                     int k = i;
25                     int min = dp[i, j];
26                     while (k >= 0 && dp[k,j] > 0)
27                     {
28                         min = Math.Min(min, dp[k, j]);
29                         curr_area = min * (i - k + 1);
30                         max_area = Math.Max(max_area, curr_area);
31                         k--;
32                     }
33                 }
34             }
35 
36             return max_area;
37         }

代码分析:

  利用DP,第一次n2循环,先预处理。然后再O(n3)计算最大面积。

  例如:

1 1 0 1
1 0 1 1
1 1 1 1
0 0 1 1

  DP处理后生成新的2D- array

1 2 0 1
1 0 1 2
1 2 3 4
0 0 1 2

 

  每个格子相应的最大面积

1 2 0 1
2 0 1 2
3 2 3 4
0 0 3 6
posted @ 2012-09-25 05:30  ETCOW  阅读(367)  评论(0编辑  收藏  举报