• 洛谷P1169 [ZJOI2007]棋盘制作 悬线法


    题目链接

    首先了解一下悬线法:《浅谈用极大化思想解决最大子矩阵问题》

    对于这道题,障碍点就是与当前点颜色相同的点,其他就照着模板做就好。

    #include <iostream>
    #include <stdio.h>
    #include <stdlib.h>
    #include <string.h>
    using namespace std;
    int n,m,bd[2010][2010],l[2010][2010],r[2010][2010],ht[2010][2010];
    
    int main()
    {
        scanf("%d%d",&n,&m);
        for(int i=1;i<=n;i++)
            for(int j=1;j<=m;j++)
            {
                scanf("%d",&bd[i][j]);
                l[i][j]=j;r[i][j]=j;ht[i][j]=1; //给悬线ij赋初值 
            }
        for(int i=1;i<=n;i++)
            for(int j=2;j<=m;j++)
                if(bd[i][j]!=bd[i][j-1])
                    l[i][j]=l[i][j-1];  //悬线ij可以向左延伸 
        for(int i=1;i<=n;i++)
            for(int j=m-1;j>=1;j--)
                if(bd[i][j]!=bd[i][j+1])
                    r[i][j]=r[i][j+1];  //悬线ij向右延伸 
        for(int i=2;i<=n;i++)
            for(int j=1;j<=m;j++)
                if(bd[i][j]!=bd[i-1][j])
                {
                    ht[i][j]=ht[i-1][j]+1;  //悬线ij向上延伸 
                    l[i][j]=max(l[i][j],l[i-1][j]);  //悬线ij收缩左区间 
                    r[i][j]=min(r[i][j],r[i-1][j]);  //收缩右区间 
                }
                
        int ans1=0,ans2=0;
        for(int i=1;i<=n;i++)
            for(int j=1;j<=m;j++)
            {
                int a=r[i][j]-l[i][j]+1,b=ht[i][j];  //悬线ij对应矩形宽为悬线ij左右延伸的距离,高为ij向上延伸距离 
                ans1=max(ans1,min(a,b)*min(a,b));  //对应正方形面积 
                ans2=max(ans2,a*b);  //矩形面积 
            }
        printf("%d
    %d
    ",ans1,ans2);
        return 0;
    }

     

  • 相关阅读:
    UVA 12284 Digital Matrix
    lightoj 1052
    light oj 1236
    light oj 1151
    省选准备 MISTAKE 大全
    我的省选 Day -15
    「FJ2014集训」采药人的路径
    【NOI2012】迷失游乐园
    寒假这十天
    计算几何 大杂烩
  • 原文地址:https://www.cnblogs.com/BakaCirno/p/11531236.html
Copyright © 2020-2023  润新知