【线段树四】HDU 2795 Billboard
时间:2014-04-29 23:55:50
收藏:0
阅读:2545
BillboardTime Limit: 20000/8000 MS (Java/Others) Memory Limit: 32768/32768 K (Java/Others)Total Submission(s): 9045 Accepted Submission(s): 4021 Problem
Description
At
the entrance to the university, there is a huge rectangular billboard of
size h*w (h is its height and w is its width). The board is the place
where all possible announcements are posted: nearest programming
competitions, changes in the dining room menu, and other important
information.
On
September 1, the billboard was empty. One by one, the announcements
started being put on the billboard.
Each
announcement is a stripe of paper of unit height. More specifically, the
i-th announcement is a rectangle of size 1 * wi. When
someone puts a new announcement on the billboard, she would always choose
the topmost possible position for the announcement. Among all possible
topmost positions she would always choose the leftmost
one. If
there is no valid location for a new announcement, it is not put on the
billboard (that‘s why some programming contests have no participants from
this university). Given
the sizes of the billboard and the announcements, your task is to find the
numbers of rows in which the announcements are placed. Input
There
are multiple cases (no more than 40 cases). The
first line of the input file contains three integer numbers, h, w, and n
(1 <= h,w <= 10^9; 1 <= n <= 200,000) - the dimensions of the
billboard and the number of announcements. Each
of the next n lines contains an integer number wi (1 <= wi <= 10^9)
- the width of i-th announcement. Output
For each announcement
(in the order they are given in the input file) output one number - the
number of the row in which this announcement is placed. Rows are numbered
from 1 to h, starting with the top row. If an announcement can‘t be put on
the billboard, output "-1" for this announcement.
Sample
Input
3 5 5
2
4
3
3
3 Sample
Output
1
2
1
3
-1 Author
hhanger@zju
Source
|
题意:
知识点:区间范围取最大值。
叶子节点代表广告牌的宽度
#include<stdio.h>
#include <algorithm>
using
namespace std;
#define MAXN 200000
int
t[MAXN*4];
int h,w,n;
void PushUp(int index){
t[index]=max(t[index*2],t[index*2+1]);
}
void
build(int l,int r,int
index){
if(l==r){
t[index]=w;
return ;
}
int mid=(l+r)/2;
build(l,mid,index*2);
build(mid+1,r,index*2+1);
PushUp(index);
}
int
Query(int width,int l,int
r,int index){
if(l==r){
t[index]-=width;
return l;//返回所在层数
}
int mid=(l+r)/2;
int hh=0;
if(t[index*2]>=width)
hh=Query(width,l,mid,index*2);
else
hh=Query(width,mid+1,r,index*2+1);
PushUp(index);
return hh;
}
int main(){
while(~scanf("%d%d%d",&h,&w,&n)){
if(h>n)//这里如果广告牌的高度大于通告的个数的话
h=n;
build(1,h,1);//是以广告牌的高度为范围建树
int wi;
for(int
i=1;i<=n;i++){
scanf("%d",&wi);
if(t[1]<wi)
printf("-1\n");
else
printf("%d\n",Query(wi,1,h,1));
}
}
return 0;
}
评论(0)