hdu 1506(好题+DP或者RMQ)
Largest Rectangle in a Histogram
Time Limit: 2000/1000 MS (Java/Others) Memory Limit: 65536/32768 K (Java/Others)
Total Submission(s): 15396 Accepted Submission(s): 4470
histogram is a polygon composed of a sequence of rectangles aligned at a
common base line. The rectangles have equal widths but may have
different heights. For example, the figure on the left shows the
histogram that consists of rectangles with the heights 2, 1, 4, 5, 1, 3,
3, measured in units where 1 is the width of the rectangles:
![](http://acm.hdu.edu.cn/data/images/1506-1.gif)
Usually,
histograms are used to represent discrete distributions, e.g., the
frequencies of characters in texts. Note that the order of the
rectangles, i.e., their heights, is important. Calculate the area of the
largest rectangle in a histogram that is aligned at the common base
line, too. The figure on the right shows the largest aligned rectangle
for the depicted histogram.
input contains several test cases. Each test case describes a histogram
and starts with an integer n, denoting the number of rectangles it is
composed of. You may assume that 1 <= n <= 100000. Then follow n
integers h1, ..., hn, where 0 <= hi <= 1000000000. These numbers
denote the heights of the rectangles of the histogram in left-to-right
order. The width of each rectangle is 1. A zero follows the input for
the last test case.
each test case output on a single line the area of the largest
rectangle in the specified histogram. Remember that this rectangle must
be aligned at the common base line.
4 1000 1000 1000 1000
0
4000
#include<stdio.h>
#include<iostream>
#include<string.h>
#include<math.h>
#include<algorithm>
using namespace std;
const int N = ;
int min_dp[N][];
long long a[N];
int L[N],R[N];
int MIN(int i,int j)
{
if(a[i]>a[j]) return j;
return i;
}
void init_RMQ(int n)
{
for(int i=; i<=n; i++)
{
min_dp[i][]=i;
}
for(int j=; (<<j)<=n; j++)
{
for(int i=; i+(<<j)-<=n; i++)
{
min_dp[i][j] = MIN(min_dp[i][j-],min_dp[i+(<<(j-))][j-]);
}
}
} int MIN_RMQ(int l,int r)
{
int k=;
while((<<(k+))<=(r-l+)) k++;
return MIN(min_dp[l][k],min_dp[r-(<<k)+][k]);
}
int binary(int value,int l,int r) ///找到最右边
{
while(l<=r)
{
if(l==r) return l;
int mid = (l+r)>>;
if(value<=a[MIN_RMQ(l,mid)])
{
l = mid+;
}
else r = mid;
} }
int binary2(int value,int l,int r) ///找到最左边
{
while(l<r)
{
if(l==r-){ ///防止死循环,这里弄了好久
if(a[r]<value) return r; ///如果在r 并且a[r]<value 那么肯定r就是左边界
return l;
}
int mid = (l+r)>>;
if(value<=a[MIN_RMQ(mid,r)])
{
r = mid-;
}
else l = mid;
}
return l;
}
int main()
{
int n;
while(scanf("%d",&n)!=EOF&&n)
{
for(int i=; i<=n; i++)
{
scanf("%lld",&a[i]);
}
init_RMQ(n);
L[]=;
R[n]=n;
for(int i=; i<=n; i++)
{
if(i!=n)
{
R[i] = binary(a[i],i+,n);
if(R[i]==n&&a[i]<=a[n]);
else R[i]--;
}
if(i!=)
{
L[i] = binary2(a[i],,i-);
if(L[i]==&&a[i]<=a[]);
else L[i]++;
}
}
long long mx = -;
for(int i=; i<=n; i++)
{
if((R[i]-L[i]+)*a[i]>mx) mx = (R[i]-L[i]+)*a[i];
}
printf("%lld\n",mx);
} }
解法二:DP 时间复杂度O(n*k) k是个很小的数
#include <stdio.h>
#include <iostream>
#include <string.h>
#include <math.h>
#include <algorithm>
using namespace std;
const int N = ;
long long a[N],L[N],R[N]; ///L[i]记录i点能够到达最左边的位置,R[i]同理
int main()
{
int n;
while(scanf("%d",&n)!=EOF&&n){
for(int i=;i<=n;i++){
scanf("%lld",&a[i]);
}
L[]=;
R[n]=n;
for(int i=;i<=n;i++){ ///先求出每个坐标最左边能到达的位置
int t = i;
while(t>&&a[i]<=a[t-]){
t = L[t-]; ///这步相当巧妙,直接实现了跳转,如果a[t-1]不小于a[i]
///的话,我们可以断定a[t-1]的最左边肯定包含a[i]的最左边.直接跳过中间的点
///时间复杂度就肯定没有O(n*n)了,应该是O(n*k) k是个比较小的数
}
L[i] = t;
}
for(int i=n-;i>=;i--){ ///找最右边
int t =i;
while(t<n&&a[i]<=a[t+]){
t = R[t+];
}
R[i] = t;
}
long long mx = -;
for(int i=;i<=n;i++){
if((R[i]-L[i]+)*a[i]>mx) mx = (R[i]-L[i]+)*a[i];
}
printf("%lld\n",mx);
}
return ;
}
hdu 1506(好题+DP或者RMQ)的更多相关文章
- HDU 1506 Largest Rectangle in a Histogram (dp左右处理边界的矩形问题)
E - Largest Rectangle in a Histogram Time Limit:1000MS Memory Limit:32768KB 64bit IO Format: ...
- HDU 4778 状压DP
一看就是状压,由于是类似博弈的游戏.游戏里的两人都是绝对聪明,那么先手的选择是能够确定最终局面的. 实际上是枚举最终局面情况,0代表是被Bob拿走的,1为Alice拿走的,当时Alice拿走且满足变换 ...
- HDOJ(HDU).2602 Bone Collector (DP 01背包)
HDOJ(HDU).2602 Bone Collector (DP 01背包) 题意分析 01背包的裸题 #include <iostream> #include <cstdio&g ...
- Bomb HDU - 3555 (数位DP)
Bomb HDU - 3555 (数位DP) The counter-terrorists found a time bomb in the dust. But this time the terro ...
- hdu 1505 && hdu1506 &&hdu 2830 && 2870 总结---------DP之状图选最大矩形
/* 多谢了“闭眼,睁眼” 同学给我一套dp专题,不然真是没接触过这种题型. 做个4个简单的,很高兴有所收获. 2013-08-06 /* HDU 1506 最基础的一道题目,其主要精髓就在于两个数组 ...
- HDU 1506 Largest Rectangle in a Histogram set+二分
Largest Rectangle in a Histogram Problem Description: A histogram is a polygon composed of a sequenc ...
- HDU 1011 树形背包(DP) Starship Troopers
题目链接: HDU 1011 树形背包(DP) Starship Troopers 题意: 地图中有一些房间, 每个房间有一定的bugs和得到brains的可能性值, 一个人带领m支军队从入口(房 ...
- HDU 1950 Bridging signals (DP)
职务地址:HDU 1950 这题是求最长上升序列,可是普通的最长上升序列求法时间复杂度是O(n*n).显然会超时.于是便学了一种O(n*logn)的方法.也非常好理解. 感觉还用到了一点贪心的思想. ...
- hdu 2296 aC自动机+dp(得到价值最大的字符串)
Ring Time Limit: 2000/1000 MS (Java/Others) Memory Limit: 32768/32768 K (Java/Others)Total Submis ...
随机推荐
- CentOS 6.5 下安装配置 mysql
如果要在Linux上做j2ee开发,首先得搭建好j2ee的开发环境,包括了jdk.tomcat.eclipse的安装(这个在之前的一篇随笔中已经有详细讲解了Linux学习之CentOS(七)--Cen ...
- P2075 [NOIP2012T5]借教室 区间更新+二分查找
P2075 [NOIP2012T5]借教室 时间: 1000ms / 空间: 131072KiB / Java类名: Main 背景 noip2012-tg 描述 在大学期间,经常需要租借教室.大到院 ...
- ARM汇编程序闪烁灯与其反汇编代码比较
/* *LED闪烁 *led.s */ #define GPJ0CON 0xE0200240 #define GPJ0DAT 0xE0200244 .global _start //把 _start ...
- Itext2.0.8 和freemarker导出pdf
这个是跟上一篇写的freemarker导出word是一块的.但是关联性不是很大.由于本人技术有限本篇导出也是根据网上大家的做出的demo混合而成.有不足的地方请大家指出.好改正,使以后看到的freem ...
- Test Index
top1 top11 top2 top1 top11 top2
- http学习 - 缓存
对缓存的理解更加深刻,缓存有一个过期时间,现在用的比较多的是 max-age,以前使用 expirt之类的, 然后就是需要向服务器验证是否是最新的,如果不是最新的则需要更新.
- 【BZOJ】3779 重组病毒
[算法]Link-Cut Tree+线段树(维护DFS序) [题解]整整三天……T_T 这篇题解比较资瓷:permui 这道题虽然树形态没有变化,但用lct写的原因在于把题目中的操作一进行了神转化:每 ...
- 24、redis中的sentinel的作用?
redis中的sentinel的作用? Redis-Sentinel是Redis官方推荐的高可用性(HA)解决方案,当用Redis做Master-slave的高可用方案时,假如master宕机了,Re ...
- IE浏览器Bug总结
每每在网上搜索IE浏览器Bug时,总是骂声一片,特别是前端工程师,每天都要面对,IE浏览器特别是IE6,存在很多Bug,对Web标准的支持也拖后腿,但不可否认,IE浏览器是曾经的霸主,它的贡献也是巨大 ...
- javascript语言中的一等公民-函数
简介 在很多传统语言(C/C++/Java/C#等)中,函数都是作为一个二等公民存在,你只能用语言的关键字声明一个函数然后调用它,如果需要把函数作为参数传给另一个函数,或是赋值给一个本地变量,又或是作 ...