题目链接:Largest Rectangle in a Histogram
题目大意: 有
n
(
n
≤
10000
)
n(n\leq10000)
n(n≤10000)个矩形,矩形的底边长为
1
1
1,高为
h
(
h
≤
1000000000
)
h(h\leq1000000000)
h(h≤1000000000),所有矩形的底边都在同一条直线上,求这些小矩形所能拼成的最大的矩形的面积是多少。
题目分析: 我们考虑如果所有小矩形的高度是单调递增的,那么就可以每次计算该高度到最后一个矩形所形成的的大矩形的面积
那么现在考虑如果有的矩形在中间“凸出”,或是“凹陷”,例如下图所示:
那么我们发现,在处理到第5个小矩形及以后的时候,前面两个比它高的矩形一定不会再被处理到(显然不能凹下去)。因此,我们只需要考虑高度递增的连续小矩形,而在出现比前一个矩形矮的矩形的时候,我们便把它之前的比它高的删去,于是我们就拿出了处理问题的有效工具——单调栈。
如果当前矩形比上一个高,那么就压入栈中,否则就不断弹出栈顶元素,直到找到比它矮的矩形,在此期间记录矩形所形成的的大矩形的底边长度,更新栈顶的矩形所形成的的大矩形的面积。
最后需要注意的是,为了保证所有的矩形都被统计,我们在循环的时候要从
1
1
1循环到
n
+
1.
n+1.
n+1.下面是完整代码。
题目代码:
#include<stdio.h>
#include<algorithm>
#include<string.h>
#include<stack>
#define LL long long
#define max(a,b)(a>b?a:b)
using namespace std;
int n,a[110000],_St[110000],w[110000],Top;
LL ans;
int main()
{
while(scanf("%d",&n)&&n){
memset(a,0,sizeof(a));
Top=0;ans=0;
int width=0;
for(int i=1;i<=n;i++)
scanf("%d",&a[i]);
for(int i=1;i<=n+1;i++){
if(a[i]>_St[Top])
_St[++Top]=a[i],w[Top]=1;
else{
int width=0;
while(_St[Top]>a[i]){
width+=w[Top];
ans=max(ans,(LL)width*_St[Top]);
--Top;
}
_St[++Top]=a[i];
w[Top]=width+1;
}
}
printf("%lld\n",ans);
}
return 0;
}
1328

被折叠的 条评论
为什么被折叠?



