L. Leverage MDT_单调栈


L. Leverage MDT_单调栈_02


L. Leverage MDT_单调栈_03

题意

给一个 L. Leverage MDT_单调栈_04 矩阵,可以选择一些行翻转。最大化全为 L. Leverage MDT_单调栈_05

  • 按列枚举
  • 对于每一列正反跑两遍单调栈即可

AC代码:

const int N = 1010;
char s[N][N];
int len[N][N];
int up[N], down[N];
int st[N], pos;
int n, m;
int ans;
int main()
{
sdd(n, m);
rep(i, 1, n)
ss(s[i] + 1);
rep(i, 1, n)
{
len[i][m] = 1;
per(j, m - 1, 1)
{
if (s[i][j] != s[i][j + 1])
len[i][j] = 1;
else
len[i][j] = len[i][j + 1] + 1;
}
}
rep(j, 1, m)
{
pos = 0;
st[0] = 0;
rep(i, 1, n)
{
while (len[st[pos]][j] >= len[i][j])
pos--;
up[i] = st[pos] + 1;
st[++pos] = i;
}
pos = 0;
st[0] = n + 1;
per(i, n, 1)
{
while (len[st[pos]][j] >= len[i][j])
pos--;
down[i] = st[pos] - 1;
st[++pos] = i;
}
rep(i, 1, n)
{
int l = len[i][j], r = down[i] - up[i] + 1;
ans = max(min(l, r) * min(l, r), ans);
}
}
pd(ans);
return 0;
}