zoukankan      html  css  js  c++  java
  • 思维 [2020牛客暑期多校训练营(第九场) The Escape Plan of Groundhog]

    思维 2020牛客暑期多校训练营(第九场) The Escape Plan of Groundhog

    题目大意:

    给一个01矩阵,问满足三个要求的子矩阵有多少个

    • 边界全部都是1
    • 内部的0和1的数量相差不能大于1
    • 宽和高必须大于1

    题解:

    考虑把行或者列当作一个整体,以行当作整体为例,枚举两列,那么只要 (O(n)) 判断两列的答案即可。

    两列的答案要按照这个性质来判断,可以考虑用前缀和维护,枚举一行,如果这一行全部都是1,那么就可以统计答案,如果不是那么就记录这个块的大小。

    这个题目卡时间比较紧,所以不能用map,可以考虑用两个数组来模拟,一个表示已经到第几种状态了,每次map一清空,表示状态往后挪一位,然后一个数组来表示此时的大小。

    #include <bits/stdc++.h>
    #define debug(x) cout<<"debug:"<<#x<<" = "<<x<<endl;
    using namespace std;
    const int maxn = 6e5+10;
    const int mod = 998244353;
    typedef long long ll;
    int a[550][550],sum[550][550],pre[550];
    int mp[maxn],vis[maxn];
    int main(){
    	int n,m;
    	scanf("%d%d",&n,&m);
    	for(int i = 1;i <= n; i++){
    		for(int j = 1;j <= m; j++){
    			scanf("%d",&a[i][j]);
    			if(!a[i][j]) a[i][j] = -1;
    			sum[i][j] = sum[i][j-1]+a[i][j];
    		}
    	}
    	int ans = 0,cnt = 1,M = 3e5;
    	for(int i = 1;i <= m; i++){
    		for(int j = i + 1;j <= m; j++){
    			int now  = 0,cur = 0,first = 1;
    			cnt++;
    			for(int k = 1;k <= n; k++){
    				if(a[k][j]==1&&a[k][i]==1&&sum[k][j-1]-sum[k][i]==j-1-i){
    					++now;
    					pre[now] = pre[now-1] + cur;
    					if(first) pre[now] = 0,first = 0;
    					ans+=vis[pre[now]+M]==cnt?mp[pre[now]+M]:0;
    					ans+=vis[pre[now]+1+M]==cnt?mp[pre[now]+1+M]:0;
    					ans+=vis[pre[now]-1+M]==cnt?mp[pre[now]-1+M]:0;
    					pre[now] += sum[k][j-1]-sum[k][i];
    					if(vis[pre[now]+M]==cnt) mp[pre[now]+M]++;
    					else mp[pre[now]+M] = 1,vis[pre[now]+M] = cnt;
    					cur = 0;
    				}
    				else if(a[k][j]==1&&a[k][i]==1){
    					cur += sum[k][j-1] - sum[k][i];
    				}
    				else{
    					now = 0,cur= 0,first = 1;
    					cnt ++;
    				}
    			}
    		}
    	}
    	printf("%d
    ",ans);
    	return 0;
    }
    
    
  • 相关阅读:
    前缀和
    B. Ilya and Queries
    BZOJ1652 [Usaco2006 Feb]Treats for the Cows
    NOIP2014提高组 酱油记
    NOIP初赛 BLESS ALL!
    BZOJ1096 [ZJOI2007]仓库建设
    BZOJ1036 [ZJOI2008]树的统计Count
    BZOJ1030 [JSOI2007]文本生成器
    BZOJ2749 [HAOI2012]外星人
    BZOJ1093 [ZJOI2007]最大半连通子图
  • 原文地址:https://www.cnblogs.com/EchoZQN/p/13461908.html
Copyright © 2011-2022 走看看