HDU 2870 Largest Submatrix -

本文提供了一道来自杭电OJ编号为2870的题目解决方案,采用C++实现,主要涉及动态规划和矩阵处理算法。通过对矩阵中元素的检查与更新,计算最大可能的值。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

题目地址:http://acm.hdu.edu.cn/showproblem.php?pid=2870


#include<iostream>
#include<cstdio>
#include<algorithm>
#include<cstring>
using namespace std;
#define max3(a,b,c) max(a,max(b,c))
const int maxn=1000+5;
const int A=0,B=1,C=2;
//解的情况肯定都是a,b,c 所以 事先全部替换成a,b,c 
char Matrix[maxn][maxn];
int l[maxn],r[maxn],h[maxn][maxn][3],M,N;
bool Check(char c1,char c2){
	if(c1=='w')	return c2=='a'||c2=='b';
	if(c1=='x') return c2=='b'||c2=='c';
	if(c1=='y') return c2=='a'||c2=='c';
	if(c1=='z') return true;
	return c1==c2;
}
int solve(int a)
{
	int maxA=0;
	for(int i=0;i<M;i++)
	{
		l[0]=0; r[N-1]=N-1;
		for(int j=1;j<N;j++){
			int t=j;
			while(t>0&&Check(Matrix[i][j],a+'a')&&Check(Matrix[i][t-1],a+'a')&&h[i][t-1][a]>=h[i][j][a]) t=l[t-1];
			l[j]=t;
		}
		for(int j=N-2;j>=0;j--){
			int t=j;
			while(t<N-1&&Check(Matrix[i][j],a+'a')&&Check(Matrix[i][t+1],a+'a')&&h[i][t+1][a]>=h[i][j][a]) t=r[t+1];
			r[j]=t;
		}
		for(int j=0;j<N;j++)
			maxA=max(maxA,(r[j]-l[j]+1)*h[i][j][a]);
	}
	return maxA;
}
int main()
{
	while(scanf("%d%d",&M,&N)!=EOF)
	{
		for(int i=0;i<M;i++){
			scanf("%s",Matrix[i]);
			for(int j=0;Matrix[i][j];j++)
			if(i==0) h[i][j][A]=h[i][j][B]=h[i][j][C]=1;
			else {
				h[i][j][A]=Check(Matrix[i-1][j],'a')&&Check(Matrix[i][j],'a')?h[i-1][j][A]+1:1;
				h[i][j][B]=Check(Matrix[i-1][j],'b')&&Check(Matrix[i][j],'b')?h[i-1][j][B]+1:1;
				h[i][j][C]=Check(Matrix[i-1][j],'c')&&Check(Matrix[i][j],'c')?h[i-1][j][C]+1:1;
			}
		}
		
		cout<<max3(solve(A),solve(B),solve(C))<<endl;
	}
	return 0;
} 


评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值