Codeforces Round #567 (Div. 2) C - Flag (枚举,方案数)

🏁 🏁 🏁

题意:一个矩形里面有多少子矩阵满足,可以按行划分成三个高度相同的区域,每区域内颜色相同,相邻区域颜色不同

注意n,m数据范围,O(n*m)的复杂度适合,枚举每个点作为矩形顶点的方案数,这里计数的一种方法就是枚举右上角,通过k值计算该点向左能延伸多远,就是该点作为右上角顶点的方案数

char s[1111][1111];
int num[1111][1111];//该点下方有多少相同颜色点
signed main()
{
	int n,m;cin>>n>>m;
	rpp(i,n) cin>>(s[i]+1);
	for(int i=n;i>=1;--i)
	{
		for(int j=1;j<=m;++j)
		{
			if(i==n||s[i][j]!=s[i+1][j]) num[i][j]=1;
			else num[i][j]=num[i+1][j]+1;
		}
	}
	ll ans=0,k=0;
	rpp(i,n) rpp(j,m)
	{
		int cnt=num[i][j];
		if(i+cnt*2<=n&&num[i+cnt][j]==cnt&&num[i+cnt*2][j]>=cnt)
		{//有一说一条件真长啊。。。
			if(j-1>=1&&s[i][j-1]==s[i][j]&&num[i][j-1]==cnt&&s[i+cnt][j-1]==s[i+cnt][j]&&num[i+cnt][j-1]==cnt&&s[i+cnt*2][j-1]==s[i+cnt*2][j]&&num[i+cnt*2][j-1]>=cnt) ++k;
			else k=1;
		}
		else k=0;
		ans+=k;
	}
	cout<<ans<<endl;
	return 0;
}

posted @ 2020-01-14 21:17  Herlo  阅读(177)  评论(0)    收藏  举报