#include<bits/stdc++.h>
#define debu
using namespace std;
const int maxn=1e3+50;
int n,m;
int g[maxn][maxn];
int up[maxn][maxn];
int lt[maxn][maxn];
int rt[maxn][maxn];
void init()
{
memset(g,0,sizeof(g));
memset(lt,0,sizeof(lt));
memset(rt,0,sizeof(rt));
memset(up,0,sizeof(up));
}
void solve()
{
int ans=0;
for(int i=0; i<n; i++)
{
int l=-1,r=m;
for(int j=0; j<m; j++)
{
if(g[i][j]==1)
{
l=j;
up[i][j]=lt[i][j]=0;
}
else
{
up[i][j]=(i==0?1:up[i-1][j]+1);
lt[i][j]=(i==0?l+1:max(lt[i-1][j],l+1));
}
}
for(int j=m-1; j>=0; j--)
{
if(g[i][j]==1)
{
r=j;
rt[i][j]=m;
}
else
{
rt[i][j]=(i==0?r-1:min(rt[i-1][j],r-1));
ans=max(ans,up[i][j]*(rt[i][j]-lt[i][j]+1));
}
}
}
printf("%d\n",ans*3);
}
int main()
{
#ifdef debug
freopen("in.in","r",stdin);
#endif // debug
int t;
scanf("%d",&t);
while(t--)
{
init();
scanf("%d%d",&n,&m);
for(int i=0; i<n; i++)
{
for(int j=0; j<m; j++)
{
char c=getchar();
while(c!='F'&&c!='R') c=getchar();
if(c=='F') g[i][j]=0;
else g[i][j]=1;
}
}
solve();
}
return 0;
}
题目地址:https://icpcarchive.ecs.baylor.edu/index.php?option=com_onlinejudge&Itemid=8&page=show_problem&problem=1030
题解:up[i][j]表示格子(i,j)向上可延伸的最大值,当该格为空格时up[i][j]=up[i-1][j]+1。lt[i][j]表示格子(i,j)向左可延伸的“运动极限”,则该格为空格时lt[i][j]=max(lt[i-1][j],l+1),l表示当前格子向左的“运动极限”。同理rt[i]j]=min(rt[i-1][j],r-1)。当该格不为空时,up,lt,rt值为0。注意当处于边界时的情况。