洛谷 P4147 玉蟾宫 (最大子矩形问题)

时间:2022-07-22 02:37:28

这道题用到了悬线法,非常牛逼,可以看这个论文。

https://blog.csdn.net/twtsa/article/details/8120269

#include<cstdio>
#include<cstring>
#include<iostream>
#include<algorithm>
#define REP(i, a, b) for(int i = (a); i < (b); i++)
#define _for(i, a, b) for(int i = (a); i <= (b); i++)
using namespace std; const int MAXN = 2123;
int l[MAXN][MAXN], r[MAXN][MAXN], h[MAXN][MAXN];
int a[MAXN][MAXN], n, m; int main()
{
scanf("%d%d", &n, &m);
_for(i, 1, n)
_for(j, 1, m)
{
char c; cin >> c;
a[i][j] = (c == 'F');
h[i][j] = 1;
l[i][j] = r[i][j] = j;
} _for(i, 1, n)
{
_for(j, 2, m)
if(a[i][j-1] && a[i][j])
l[i][j] = l[i][j-1];
for(int j = m - 1; j >= 1; j--)
if(a[i][j+1] && a[i][j])
r[i][j] = r[i][j+1];
} int ans = 0;
_for(i, 1, n)
_for(j, 1, m)
{
if(i > 1 && a[i][j] && a[i-1][j])
{
h[i][j] = h[i-1][j] + 1;
l[i][j] = max(l[i][j], l[i-1][j]);
r[i][j] = min(r[i][j], r[i-1][j]);
}
ans = max(ans, (r[i][j] - l[i][j] + 1) * h[i][j]);
}
printf("%d\n", 3 * ans); return 0;
}