Billboard

Time Limit: 20000/8000 MS (Java/Others)    Memory Limit: 32768/32768 K (Java/Others)

Total Submission(s): 14337    Accepted Submission(s): 6148

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
HDOJ 2009 Summer Exercise(5)



题目大意:在一块h*w的黑板上贴广告。尽量往左上角贴,每张广告高度为1。对每次贴一张广告询问广告能贴在第几行(假设不能贴就输出-1)。

思路:数据非常大,但不用离散化。由于广告高度为1,最多200000张广告。最差就是每行贴一张。

所以当h>n的时候,能够令h=n。

方法是线段树。首先建树,每一个点代表每行的剩余长度,对于一个区间能够找出其最大的剩余长度。

查询的时候假设左子树能够插入就往左子树插,左子树不行就看右子树,假设两者都不行就表示不能贴这张广告。

 
#include<stdio.h>
#include<string.h>
#define M 220005
struct tree{
int l,r,len;
}tree[M<<2];
int h,W,n,w[M];
int max(int a,int b)
{
if(a>b)return a;
else return b;
}
void build(int l,int r,int root)
{
tree[root].l=l;
tree[root].r=r;
tree[root].len=W;
if(l==r){
return;
}
int mid=l+r>>1;
build(l,mid,root<<1);
build(mid+1,r,root<<1|1);
} void pushup(int root)
{
if(tree[root].l==tree[root].r)return;
tree[root].len=max(tree[root<<1].len,tree[root<<1|1].len);
}
void update(int root,int z)
{ if(tree[root].l==tree[root].r){
tree[root].len=tree[root].len-z;
printf("%d\n",tree[root].l); return ;
}
if(tree[root<<1].len>=z)update(root<<1,z); //假设左边能够,就往左插。
else if(tree[root<<1|1].len>=z)update(root<<1|1,z); //否则往右插。 pushup(root);
}
int main()
{
int i,j,k;
while(scanf("%d%d%d",&h,&W,&n)!=EOF)
{
if(h>n)h=n;
build(1,h,1);
for(i=1;i<=n;i++)
{
scanf("%d",&w[i]);
if(tree[1].len<w[i])printf("-1\n"); //假设1-h行里面都没有一行能够让该海报贴,就输出-1
else
update(1,w[i]);
}
}
return 0;
}

hdu 2795 Billboard(线段树单点更新)的更多相关文章

  1. hdu 2795 Billboard 线段树单点更新

    Billboard Time Limit: 1 Sec  Memory Limit: 256 MB 题目连接 http://acm.hdu.edu.cn/showproblem.php?pid=279 ...

  2. HDU 2795 Billboard (线段树单点更新 && 求区间最值位置)

    题意 : 有一块 h * w 的公告板,现在往上面贴 n 张长恒为 1 宽为 wi 的公告,每次贴的地方都是尽量靠左靠上,问你每一张公告将被贴在1~h的哪一行?按照输入顺序给出. 分析 : 这道题说明 ...

  3. HDU 2795 Billboard 线段树,区间最大值,单点更新

    Billboard Time Limit: 20000/8000 MS (Java/Others)    Memory Limit: 32768/32768 K (Java/Others) Total ...

  4. HDU 2795 Billboard (线段树+贪心)

    手动博客搬家:本文发表于20170822 21:30:17, 原地址https://blog.csdn.net/suncongbo/article/details/77488127 URL: http ...

  5. HDU 2795 Billboard (线段树)

    题目链接:http://acm.hdu.edu.cn/showproblem.php?pid=2795 题目大意:有一块h*w的矩形广告板,要往上面贴广告;   然后给n个1*wi的广告,要求把广告贴 ...

  6. HDU 3308 LCIS(线段树单点更新区间合并)

    LCIS Given n integers. You have two operations: U A B: replace the Ath number by B. (index counting ...

  7. ACM学习历程—HDU 2795 Billboard(线段树)

    Description At the entrance to the university, there is a huge rectangular billboard of size h*w (h ...

  8. hdu 5480 Conturbatio 线段树 单点更新,区间查询最小值

    Conturbatio Time Limit: 1 Sec Memory Limit: 256 MB 题目连接 http://acm.hdu.edu.cn/showproblem.php?pid=54 ...

  9. [HDU] 2795 Billboard [线段树区间求最值]

    Billboard Time Limit: 20000/8000 MS (Java/Others)    Memory Limit: 32768/32768 K (Java/Others)Total ...

  10. HDU 2795 Billboard 线段树活用

    题目大意:在h*w 高乘宽这样大小的 board上要贴广告,每个广告的高均为1,wi值就是数据另给,每组数组给了一个board和多个广告,要你求出,每个广告应该贴在board的哪一行,如果实在贴不上, ...

随机推荐

  1. vue 指令的用法

    <!DOCTYPE html> <html lang="en"> <head> <meta charset="UTF-8&quo ...

  2. linux安装lrzsz支持rz从windows上传文件到linux

    1.下载lrzsz wget https://wangxuejin-data-1252194948.cos.ap-shanghai.myqcloud.com/lrzsz-0.12.20.tar.gz ...

  3. python垃圾回收算法

    标准python垃圾回收器由两部分组成,即引用计数回收器和分代垃圾回收器(即python包中的gc module).其中,引用计数模块不能被禁用,而GC模块可以被禁用. 引用计数算法 python中每 ...

  4. caioj 1063 动态规划入门(一维一边推1:美元和马克)

    这道题一开始我是这么想的 最后的答案肯定是某次的马克换回来的,但这个该怎么确定?? 实际上应该把范围缩小,只看最后一次和倒数第二次之间有什么联系. 可以发现,只有两种可能,最后一天换或者不换.换的话就 ...

  5. 在idea 中使用try catch

    ctrl+alt + t 选中代码,按快捷键可直接try catch 此段代码

  6. Junit4.x高级使用方法具体解释(一)

    近期整理代码的时候,总习惯把一些经常使用的工具类和方法等都写在junit中,这样能够方便于在想用的时候直接copy,在用junit的时候学到了一些比較实用的东西.记录例如以下: 1.使用junit进行 ...

  7. &lt;LeetCode OJ&gt; 20. Valid Parentheses

    Given a string containing just the characters '(', ')', '{', '}', '[' and ']', determine if the inpu ...

  8. Cocos2d-x手机游戏开发与项目实践具体解释_随书代码

    Cocos2d-x手机游戏开发与项目实战具体解释_随书代码 作者:沈大海  因为原作者共享的资源为UTF-8字符编码.下载后解压在win下显示乱码或还出现文件不全问题,现完整整理,解决全部乱码问题,供 ...

  9. 測试password强度

    <html> <!--激情在最后面.请看最后面红色字 这是是个计算password强度的实例 网上有非常多这种样例 只是呢,都不怎么好 这是我写的一个完整的效果,能够通用, new一 ...

  10. 聊聊高并发(十九)理解并发编程的几种&quot;性&quot; -- 可见性,有序性,原子性

    这篇的主题本应该放在最初的几篇.讨论的是并发编程最基础的几个核心概念.可是这几个概念又牵扯到非常多的实际技术.比方Java内存模型.各种锁的实现,volatile的实现.原子变量等等,每个都可以展开写 ...