Largest Square (简单DP)

emmmm,不知道出处。。。。

题目大意:给你$n imes n$的01矩阵,让你找到最大的0方阵的面积

Sample Input

4 5
0 0 1 0 0
1 0 0 0 0
0 0 0 1 0
0 0 0 1 0

Sample Output

4

emmm,挺简单的。。。没考虑到全是1的情况WA了挺久的。。。。

1.每个格子能组成的最大方阵都是由上、左、左上3个格子决定的,我们直接取3个的最小边长+1就好了

以下是AC代码:

#include <cstdio>
#include <cstring>
#include <algorithm>
using namespace std;

const int mac=1500;

int mp[mac][mac],dp[mac][mac];

int main()
{
    int n,m,ans=0;
    scanf ("%d%d",&n,&m);
    for (int i=1; i<=n; i++)
        for (int j=1; j<=m; j++)
            scanf ("%d",&mp[i][j]);
    for (int i=1; i<=n; i++){
        for (int j=1; j<=m; j++){
            if (mp[i][j]) dp[i][j]=0;
            else dp[i][j]=min(min(dp[i-1][j],dp[i-1][j-1]),dp[i][j-1])+1;
            ans=max(ans,dp[i][j]);
        }
    }    
    printf("%d
",ans*ans);
    return 0;
}
View Code

2.先预处理每个格子能向左、向上延伸的最大长度,然后判断能否包含左上角的最大方阵,如果能就直接对$dp[i-1][j-1]$开方,然后+1再平方,如果不能,那么此格的边长就是$min(left[i][j],up[i][j])$

以下是AC代码:

#include <cstdio>
#include <cstring>
#include <algorithm>
using namespace std;

const int mac=1500;

int mp[mac][mac],dp[mac][mac];
int left[mac][mac],up[mac][mac];//向左,向上延伸的长度

int main()
{
    int n,m,ans=0;
    scanf ("%d%d",&n,&m);
    for (int i=1; i<=n; i++)
        for (int j=1; j<=m; j++){
            scanf ("%d",&mp[i][j]);
            if (!mp[i][j]) dp[i][j]=1;
        }

    for (int i=1; i<=n; i++){
        int cnt=0;
        for (int j=1; j<=m; j++){
            if (mp[i][j]==0) left[i][j]=++cnt;
            else cnt=0;
        }
    }
    for (int j=1; j<=m; j++){
        int cnt=0; 
        for (int i=1; i<=n; i++){
            if (mp[i][j]==0) up[i][j]=++cnt;
            else cnt=0;
        }
    }
    for (int i=1; i<=n; i++){
        for (int j=1; j<=m; j++){
            if (mp[i][j]) continue;
            if (mp[i-1][j-1]==0){
                int p=sqrt(dp[i-1][j-1]);
                if (left[i][j]<p+1 || up[i][j]<p+1){
                    int use=min(left[i][j],up[i][j]);
                    dp[i][j]=use*use;
                    ans=max(ans,dp[i][j]);
                    continue;
                }
                p++;
                dp[i][j]=p*p;
                ans=max(ans,dp[i][j]);
            }
        }
    }
    printf("%d
",ans);
    return 0;
}
View Code
路漫漫兮
原文地址:https://www.cnblogs.com/lonely-wind-/p/13245776.html