• Codeforces 1200D White Lines 二维差分


    题目链接:https://www.luogu.org/problem/CF1200D

    题意:

    分析:对每行每列单独进行分析,以行举例

    对于每一行,找出最左边的黑点和最右边的黑点(可能为一个),如果不存在就先将答案+1,并跳过该行

    如果两点长度大于K,则不可能有矩形满足将该行变为全白行,跳过该行

    如果小于k的话,说明存在点能够将该行变为全白行,设该行为第i行的话,左右黑点纵坐标分别为l,r,我们发现坐标范围在(i-k+1,r-k+1)~(i,l)之间的点都可以将该行变为全白行

    我们可以考虑用一个二维的差分数组来记录变化,diff[i][j]表示从(0,0)到(i,j)的变化值

    那显然我们可以将diff[i][l]++,diff[i-k][l]--,diff[i][r-k]--,在将被多减了一次的diff[i-k][r-k]+1,然后从点(n,n)开始,向前递推,求出每个点可以变白行的值

    令x=rk+1,y=l,递推式即为:pra[i][j]=pra[i+1][j]+pra[i][j+1]pra[i+1][j+1]+sum[i][j]

    代码实现过程要注意数组越界情况

    #include<bits/stdc++.h>
    using namespace std;
    typedef long long ll;
    const int inf=0x3f3f3f3f;
    #define mem0(a) memset(a,0,sizeof(a))
    #define meminf(a) memset(a,0x3f,sizeof(a))
    #define ls rt<<1
    #define rs rt<<1|1
    typedef unsigned long long ull;
    const int maxn=150010;
    const int mod=1e9+7;
    char a[2010][2010];
    int diff[2010][2010];
    int pre[2010][2010];
    int main(){
        int n,k;scanf("%d%d",&n,&k);
        for(int i=1;i<=n;i++){
            scanf("%s",a[i]+1);
        }
        //line operation
        int ans=0;
        for(int i=1;i<=n;i++){
            int l=n+1,r=0;
            for(int j=1;j<=n;j++){
                if(a[i][j]=='B'){
                    l=min(l,j);
                    r=max(r,j);
                }
            }
            if(l==n+1) {
                ans++;continue;
            }
            if(r-l>=k)continue;
            int x=max(1,r-k+1),y=l;//可行区域的左右边界 
            diff[i][y]++;diff[i][x-1]--;
            if(i>=k)diff[i-k][y]--,diff[i-k][x-1]++;
        }
        //row operation
        for(int i=1;i<=n;i++){
            int u=n+1,d=0;
            for(int j=1;j<=n;j++){
                if(a[j][i]=='B'){
                    u=min(u,j);
                    d=max(d,j);
                }
            }
            if(u==n+1){
                ans++;continue;
            }
            if(d-u>=k)continue;
            int x=max(1,d-k+1),y=u;//可行区域的上下边界
            diff[y][i]++; diff[x-1][i]--;
            if(i>=k)diff[y][i-k]--,diff[x-1][i-k]++;
        }
        int res=0;
        for(int i=n;i>=1;i--){
            for(int j=n;j>=1;j--){
                pre[i][j]=pre[i+1][j]+pre[i][j+1]-pre[i+1][j+1]+diff[i][j];
                res=max(res,pre[i][j]);
            }
        }
        printf("%d
    ",ans+res);
        return 0;
    }
  • 相关阅读:
    内容收缩伸展
    分页浏览的导航栏Bootstrap和js两种方法
    Bootstrap-缩略图
    Bootstrap-进度条
    Bootstrap-点击“&#215;”,可以关闭页面
    Bootstrap页头
    Bootstrap分页
    Bootstrap--面包屑路径导航
    Bootstrap--标签和徽章<新闻后面的new hot等>
    NSLog 去除上线版本
  • 原文地址:https://www.cnblogs.com/qingjiuling/p/11678883.html
Copyright © 2020-2023  润新知