HDU2870 Largest Submatrix(单调栈,最大矩形面积)

传送门
写dp的时候莫名其妙写到了这题,其实就是一个单调栈的模板题.观察后可以发现最后矩阵由’a’或者’b’或者’c’组成的时候能得到的最大子矩阵是最优的.所以枚举三种情况跑一遍单调栈维护一个递增的矩形就好了.
代码

#pragma GCC optimize(2)
#define LL long long
#define pq priority_queue
#define ULL unsigned long long
#define pb push_back
#define mem(a,x) memset(a,x,sizeof a)
#define pii pair<int,int>
#define fir(i,a,b) for(int i=a;i<=(int)b;++i)
#define afir(i,a,b) for(int i=(int)a;i>=b;--i)
#define ft first
#define vi vector<int>
#define sd second
#define ALL(a) a.begin(),a.end()
#define bug puts("-------")
#define mpr(a,b) make_pair(a,b)
#include <bits/stdc++.h>

using namespace std;
const int N = 1e3+10;

inline void read(int &a){
    
    
	int x = 0,f=1;char ch = getchar();
	while(ch<'0'||ch>'9'){
    
    if(ch=='-')f=-1;ch=getchar();}
	while(ch<='9'&&ch>='0'){
    
    x=x*10+ch-'0';ch=getchar();}
	a = x*f;
}

string org[N];
int n,m,mz[N][N],h[N][N],s[N],w[N];

int solve(){
    
    
	int ans = 0;
	mem(h,0);
	mem(s,0);
	mem(w,0);
	fir(i,1,n){
    
    
		int cnt = 0;
		fir(j,1,m+1){
    
    
			if(j != m+1 && mz[i][j] == 1) h[i][j] = h[i-1][j] + 1;
			else h[i][j] = 0;
			int width = 0;
			while(cnt && h[i][j] <= h[i][s[cnt]]){
    
    
				width += w[cnt];
				ans = max(ans,h[i][s[cnt]]*width);
				cnt--;
			}
			s[++cnt] = j;
			w[cnt] = width+1;
		}
	}

	return ans;
}

int main(){
    
    
    while(cin >> n >> m){
    
    
    	fir(i,0,n-1)
    		cin >> org[i];
    	fir(i,0,n-1){
    
    
    		fir(j,0,m-1){
    
    
    			if(org[i][j] == 'a' || org[i][j] == 'w' || org[i][j] == 'y' || org[i][j] == 'z') mz[i+1][j+1] = 1;
    			else mz[i+1][j+1] = 0;
    		}
    	}
    	int ans = solve();
    	fir(i,0,n-1){
    
    
    		fir(j,0,m-1){
    
    
    			if(org[i][j] == 'b' || org[i][j] == 'w' || org[i][j] == 'x' || org[i][j] == 'z') mz[i+1][j+1] = 1;
    			else mz[i+1][j+1] = 0;
    		}
    	}
    	ans = max(ans,solve());
    	fir(i,0,n-1){
    
    
    		fir(j,0,m-1){
    
    
    			if(org[i][j] == 'c' || org[i][j] == 'x' || org[i][j] == 'y' || org[i][j] == 'z') mz[i+1][j+1] = 1;
    			else mz[i+1][j+1] = 0;
    		}
    	}
    	ans = max(ans,solve());
    	cout << ans << endl;
    }
	
	return 0;
}	

猜你喜欢

转载自blog.csdn.net/weixin_45590210/article/details/108554604