poj 3667 Hotel (线段树)
http://poj.org/problem?id=3667
Time Limit: 3000MS | Memory Limit: 65536K | |
Total Submissions: 9484 | Accepted: 4066 |
Description
The cows are journeying north to Thunder Bay in Canada to gain cultural enrichment and enjoy a vacation on the sunny shores of Lake Superior. Bessie, ever the competent travel agent, has named the Bullmoose Hotel on famed Cumberland Street as their vacation residence. This immense hotel has N (1 ≤ N ≤ 50,000) rooms all located on the same side of an extremely long hallway (all the better to see the lake, of course).
The cows and other visitors arrive in groups of size Di (1 ≤ Di ≤ N) and approach the front desk to check in. Each group i requests a set of Di contiguous rooms from Canmuu, the moose staffing the counter. He assigns them some set of consecutive room numbers r..r+Di-1 if they are available or, if no contiguous set of rooms is available, politely suggests alternate lodging. Canmuu always chooses the value of r to be the smallest possible.
Visitors also depart the hotel from groups of contiguous rooms. Checkout i has the parameters Xi and Di which specify the vacating of rooms Xi ..Xi +Di-1 (1 ≤ Xi ≤ N-Di+1). Some (or all) of those rooms might be empty before the checkout.
Your job is to assist Canmuu by processing M (1 ≤ M < 50,000) checkin/checkout requests. The hotel is initially unoccupied.
Input
* Line 1: Two space-separated integers: N and M * Lines 2..M+1: Line i+1 contains request expressed as one of two possible formats: (a) Two space separated integers representing a check-in request: 1 and Di (b) Three space-separated integers representing a check-out: 2, Xi, and Di
Output
* Lines 1.....: For each check-in request, output a single line with a single integer r, the first room in the contiguous sequence of rooms to be occupied. If the request cannot be satisfied, output 0.
Sample Input
10 6
1 3
1 3
1 3
1 3
2 5 5
1 6
Sample Output
1
4
7
0
5
Source
{
int l,r;
int ml,mm,mr; //左边的空位,区间最大的空位,右边的空位
}node[N<<2];
/**
judge status: Accepted exe.time:563MS
exe.memory 2712K language:C++
*/ #include<iostream>
#include<stdio.h>
#include<string.h>
#include<algorithm> #define N 50010 #define lson p<<1
#define rson p<<1|1 using namespace std; struct Nod
{
int l,r;
int ml,mm,mr; //左边的空位,区间最大的空位,右边的空位
}node[N<<]; int id; void building(int l,int r,int p)//建树
{
node[p].l = l;
node[p].r = r;
node[p].mm=node[p].mr=node[p].ml= r-l+;
if(l==r) return;
int mid = (l+r)>>;
building(l,mid,lson);
building(mid+,r,rson);
} void judgeChange(int p) //向下更新,状态延迟标记,当搜索到整个区间一样时,向下更新一层,然后进行操作
{
if(node[p].mm==node[p].r-node[p].l+)
{
node[lson].ml=node[lson].mm=node[lson].mr=node[lson].r-node[lson].l+;
node[rson].ml=node[rson].mm=node[rson].mr=node[rson].r-node[rson].l+;
}
if(node[p].mm==)
{
node[lson].ml=node[lson].mm=node[lson].mr=;
node[rson].ml=node[rson].mm=node[rson].mr=;
}
} void findId(int p,int val) //查找可以开房间的起始位置
{
if(node[p].l==node[p].r&&val==) //当val为1并且已经达到叶子节点,说明没有孩子了,不必再往下查找
{
id = node[p].l;
return;
}
judgeChange(p); //状态延迟标记更新
if(node[p].mm>=val) //区间最大连续>=val时
{
if(node[lson].mm>=val) //优先左边搜索
{
findId(lson,val);
}
else if(node[rson].ml+node[lson].mr>=val) //然后中间
{
id = node[lson].r - node[lson].mr + ;
}
else if(node[rson].mm>=val) //最后右边
{
findId(rson,val);
}
}
} void Up(int p) //向上更新状态
{
node[p].ml = node[lson].ml;
node[p].mr = node[rson].mr;
if(node[lson].ml==node[lson].r-node[lson].l+)
{
node[p].ml+=node[rson].ml;
}
if(node[rson].mr==node[rson].r-node[rson].l+)
{
node[p].mr+=node[lson].mr;
}
node[p].mm = max(node[lson].mm,node[rson].mm);
node[p].mm = max(node[p].mm,node[lson].mr+node[rson].ml);
node[p].mm = max(node[p].mm,node[p].ml);
node[p].mm = max(node[p].mm,node[p].mr);
} void update(int l,int r,int p,int op) //更新
{
if(node[p].l==l&&node[p].r==r)
{
if(op==) node[p].ml=node[p].mm=node[p].mr=; //执行操作1
else node[p].ml=node[p].mm=node[p].mr=r-l+; //执行操作2
return;
}
judgeChange(p); //状态延迟标记更新
int mid = (node[p].l+node[p].r)>>;
if(r<=mid) update(l,r,lson,op);
else if(l>mid) update(l,r,rson,op);
else
{
update(l,mid,lson,op);
update(mid+,r,rson,op);
}
Up(p); //由左右孩子节点向上更新ml,mm,mr值
} int main()
{
int n,m;
scanf("%d%d",&n,&m);
building(,n,);
while(m--)
{
int op,a,b;
scanf("%d",&op);
if(op==)
{
scanf("%d",&a);
id = ;
findId(,a); //查找可插入位置
printf("%d\n",id);
if(id) update(id,id+a-,,); //在id位置插入a个数,即在[id,id+a-1]插入
}
else if(op==)
{
scanf("%d%d",&a,&b);
update(a,a+b-,,); //在a位置删除b个数,即把在[a,a+b-1]区间清空
}
}
return ;
}
poj 3667 Hotel (线段树)的更多相关文章
- POJ 3667 Hotel(线段树 区间合并)
Hotel 转载自:http://www.cnblogs.com/scau20110726/archive/2013/05/07/3065418.html [题目链接]Hotel [题目类型]线段树 ...
- POJ 3667 Hotel (线段树区间合并)
题目链接:http://poj.org/problem?id=3667 最初给你n间空房,m个操作: 操作1 a 表示检查是否有连续的a间空房,输出最左边的空房编号,并入住a间房间. 操作2 a b ...
- poj 3667 Hotel(线段树,区间合并)
Hotel Time Limit: 3000MSMemory Limit: 65536K Total Submissions: 10858Accepted: 4691 Description The ...
- PKU 3667 Hotel(线段树)
Hotel The cows are journeying north to Thunder Bay in Canada to gain cultural enrichment and enjoy a ...
- POJ 1823 Hotel 线段树
题目链接 线段树的区间合并. 和上一题差不多....第三种操作只需要输出maxx[1]的值就可以. #include <iostream> #include <vector> ...
- 线段树(区间合并) POJ 3667 Hotel
题目传送门 /* 题意:输入 1 a:询问是不是有连续长度为a的空房间,有的话住进最左边 输入 2 a b:将[a,a+b-1]的房间清空 线段树(区间合并):lsum[]统计从左端点起最长连续空房间 ...
- POJ 3667 Hotel(线段树)
POJ 3667 Hotel 题目链接 题意:有n个房间,如今有两个操作 1.找到连续长度a的空房间.入住,要尽量靠左边,假设有输出最左边的房间标号,假设没有输出0 2.清空[a, a + b - 1 ...
- POJ.2299 Ultra-QuickSort (线段树 单点更新 区间求和 逆序对 离散化)
POJ.2299 Ultra-QuickSort (线段树 单点更新 区间求和 逆序对 离散化) 题意分析 前置技能 线段树求逆序对 离散化 线段树求逆序对已经说过了,具体方法请看这里 离散化 有些数 ...
- [USACO08FEB]酒店Hotel 线段树
[USACO08FEB]酒店Hotel 线段树 题面 其实就是区间多维护一个lmax,rmax(表示从左开始有连续lmax个空房,一直有连续rmax个空房到最右边),合并时讨论一下即可. void p ...
随机推荐
- Android_listView
package com.example.app5; import java.util.ArrayList; import java.util.HashMap; import java.util.Lis ...
- Linux Shell产生16进制随机数
n为字符长度 openssl rand -hex n
- 类结构体 与 byte[] 转换类
public static class StructConvert { public static object BytesToStruct(byte[] bytes, Type strcutType ...
- solr-tomcat 中文乱码
<Connector URIEncoding="UTF-8" port="8080" protocol="HTTP/1.1" conn ...
- 日志记录类LogHelper
开源日志log4net使用起来很方便,但是项目中不让用,所以自己重写了一个类,用来记录日志,比较简单. 1.首先是可以把日志分成多个类型,分别记录到不同的文件中 /// <summary> ...
- java多线程总结五:线程池的原理及实现
1.线程池简介: 多线程技术主要解决处理器单元内多个线程执行的问题,它可以显著减少处理器单元的闲置时间,增加处理器单元的吞吐能力. 假设一个服务器完成一项任务所需时间为:T1 创 ...
- IO流详解(半教材类型)
这两天学习了IO流,整理了一些理论知识点,仅供参考. java流概述 一 流 从操作系统层面和文件系统,数据保存相关的是所有语言都具备的一个基本功能,java专门开发了一个包:java.io.*;ja ...
- Oracle之初始创建scott/tiger来测试
在redhat5.5(32bit)上安装好oracle11g数据库软件,然后安装一个数据库,再然后登录数据库,创建scott/tiger测试 首先登录数据库,这里登录时是没有启动数据库的 [oracl ...
- gradle使用国内源
// 设置 maven 库地址 repositories { maven { url 'http://maven.oschina.net/content/groups/public/' } } ...
- seaJs 使用
开始使用seajs的时候折磨了我好一阵.光是各种概念就让新手难理解.现在弄清楚了,上个实践以备忘.目录结构如图. 1.文件 sea.html main.js a.js b.js c.js 最 ...