1 条题解
- 
  1
解决这个问题之前我们先讲一个新知识点,对于一行连续的柱形图,如何求出最大的矩形面积。

设当前柱形高度为 , 为当前元素左边第一个高度小于它的柱形的位置, 为右边第一个,计 为扩展出的矩形的面积 ,最终答案为所有的 取最大。
/** * author: 小飞侠 * created: 2024.12.11 15:59:04 */ #include <iostream> using namespace std; const int N = 3010; int l[N], r[N], q[N]; int g[N][N], h[N][N]; int n, m, p; int res; int cal(int h[])//计算这一行为底的最大矩形面积 { int top = 0; l[0] = -1, h[m + 1] = -1; for(int i = 1; i <= m; ++ i) { while(top && h[q[top]] >= h[i]) -- top; if(!top) l[i] = 0; else l[i] = q[top]; q[++ top] = i; }//l[m]存储 m 个元素左边第一个小于他的元素的位置 top = 0; for(int i = m; i >= 1; -- i) { while(top && h[q[top]] >= h[i]) -- top; if(!top) r[i] = m + 1; else r[i] = q[top]; q[++ top] = i; }//r[m]存储 m 个元素右边第一个小于他的元素的位置 int res = 0; for(int i = 1; i <= m; ++ i) res = max(res, (r[i] - l[i] - 1) * h[i]);//所有的 t return res; } int main() { cin >> n >> m >> p; while(p --) { int x, y; cin >> x >> y; g[x][y] = 1; } for(int i = 1; i <= n; ++ i) { for(int j = 1; j <= m; ++ j) { if(!g[i][j]) h[i][j] = h[i - 1][j] + 1; } }//用 h 数组模拟出柱形图 //h[i] 这一行数表示的是第 i 行为底的柱形图每一列的高度 for(int i = 1; i <= n; ++ i) res = max(res, cal(h[i]));//暴力枚举任意一行为底部的柱形图 cout << res << '\n'; return 0; } 
- 1
 
信息
- ID
 - 5520
 - 时间
 - 1000ms
 - 内存
 - 256MiB
 - 难度
 - 5
 - 标签
 - 递交数
 - 8
 - 已通过
 - 2
 - 上传者