题意:

给出平面上一些线段,在线询问与x=x0相交的线段中,交点y最大的线段的标号,支持添加线段。

大概思路:

用线段树维护,线段树每个线段记录贯穿(左右端点在该区间外或上)的原线段中能覆盖其它贯穿该线段的原线段(即每个线段树线段记录贯穿该线段的所有原线段中“最高”的)

细节:

添加原线段s到线段树线段nd:

如果s不能覆盖,根据s的大小传递到左儿子或右儿子或都传

如果s覆盖,

如果原本没有线段,则直接设置为s

   如果有线段ss,求s与ss的交点,将短(比较x上投影的长度)的线段“压”到交点所在儿子,长的变成本区间的。

  (要注意如果y相等,比较标号)

查询x

  查询覆盖x的所有区间的线段树线段对应的原线段(有的话)中在x处y最大的。

 /**************************************************************
Problem: 3165
User: idy002
Language: C++
Result: Accepted
Time:1492 ms
Memory:4244 kb
****************************************************************/ #include <cstdio>
#include <cmath>
#include <vector>
#define lson nd<<1
#define rson nd<<1|1
#define maxn 100010
#define modx 39989
#define mody 1000000000
#define eps 1e-10
using namespace std; int sg( double x ) {
return (x>-eps)-(x<eps);
}
struct Line {
int lf, rg;
double k, b;
Line(){}
Line( int x0, int y0, int x1, int y1 ) {
lf = min( x0, x1 );
rg = max( x0, x1 );
if( x0==x1 ) {
k = 0.0;
b = max( y0, y1 );
} else {
k = (y1-y0+0.0)/(x1-x0);
b = y1-x1*k;
}
}
inline double f( int x ) {
return k*x+b;
}
inline double cx( Line &c ) {
return (c.b-b)/(k-c.k);
}
}; int n;
int ltot;
Line lns[maxn];
int v[(modx+)<<];
int wi[modx+];
double wy[modx+]; void update( int x, int i ) {
double ny = lns[i].f(x);
int s=sg(ny-wy[x]);
if( !wi[x] || (s> || (s==&&i<wi[x])) ) {
wi[x] = i;
wy[x] = ny;
}
}
void modify( int i, int nd, int lf, int rg ) {
if( lns[i].lf<=lf && rg<=lns[i].rg ) {
if( !v[nd] ) {
v[nd] = i;
return;
}
bool lu = sg( lns[i].f(lf)-lns[v[nd]].f(lf) )>;
bool ru = sg( lns[i].f(rg)-lns[v[nd]].f(rg) )>;
int mid=(lf+rg)>>;
if( lu && ru ) {
v[nd] = i;
} else if( lu || ru ) {
int lm = floor( lns[i].cx( lns[v[nd]] ) );
if( lm<=mid && lu ) {
modify( i, lson, lf, mid );
} else if( lm<=mid && ru ) {
modify( v[nd], lson, lf, mid );
v[nd] = i;
} else if( lu ) {
modify( v[nd], rson, mid+, rg );
v[nd] = i;
} else {
modify( i, rson, mid+, rg );
}
} else {
update( lf, i );
update( rg, i );
}
return;
}
int mid = (lf+rg)>>;
if( lns[i].lf<=mid ) modify( i, lson, lf, mid );
if( lns[i].rg>mid ) modify( i, rson, mid+, rg );
}
int query( int x ) {
int nd = ;
int lf = , rg = modx;
int rt = ;
double cury = -1.0;
while() {
if( v[nd] ) {
double ny = lns[v[nd]].f(x);
int s = sg( ny-cury );
if( s> || (s==&&v[nd]<rt) ) {
rt = v[nd];
cury = ny;
}
}
if( lf==rg ) break;
int mid=(lf+rg)>>;
if( x<=mid ) {
nd = lson;
rg=mid;
} else {
nd = rson;
lf=mid+;
}
}
int s = sg( wy[x]-cury );
if( s> || (s==&&wi[x]<rt) )
return wi[x];
return rt;
} int main() {
int T, lastans=;
scanf( "%d", &T );
while( T-- ) {
int opt;
scanf( "%d", &opt );
if( opt== ) {
int x;
scanf( "%d", &x );
x = ((x+lastans-)%modx+);
printf( "%d\n", lastans=query(x) );
} else {
int x0, y0, x1, y1;
scanf( "%d%d%d%d", &x0, &y0, &x1, &y1 );
x0 = (x0+lastans-)%modx+;
y0 = (y0+lastans-)%mody+;
x1 = (x1+lastans-)%modx+;
y1 = (y1+lastans-)%mody+;
lns[++ltot] = Line(x0,y0,x1,y1);
modify( ltot, , , modx );
}
}
}

bzoj 3165的更多相关文章

  1. bzoj 3165: [Heoi2013]Segment 动态凸壳

    3165: [Heoi2013]Segment Time Limit: 40 Sec  Memory Limit: 256 MBSubmit: 202  Solved: 89[Submit][Stat ...

  2. BZOJ.3165.[HEOI2013]Segment(李超线段树)

    BZOJ 洛谷 对于线段,依旧是存斜率即可. 表示精度误差一点都不需要管啊/托腮 就我一个人看成了mod(10^9+1)吗.. //4248kb 892ms #include <cstdio&g ...

  3. BZOJ 3165: [Heoi2013]Segment

    3165: [Heoi2013]Segment Time Limit: 40 Sec  Memory Limit: 256 MBSubmit: 465  Solved: 187[Submit][Sta ...

  4. Bzoj 3165 [Heoi2013]Segment题解

    3165: [Heoi2013]Segment Time Limit: 40 Sec  Memory Limit: 256 MBSubmit: 668  Solved: 276[Submit][Sta ...

  5. 【BZOJ 3165】【HEOI 2013】Segment

    往区间上覆盖一次函数,做法是用线段树维护标记永久化. 每次都忘了线段树要4倍空间,第一次交总是RE,再这么手残的话考场上就真的要犯逗了. #include<cstdio> #include ...

  6. BZOJ 3165 Segment

    同上题. #include<iostream> #include<cstdio> #include<cstring> #include<algorithm&g ...

  7. 【BZOJ 3165】 [Heoi2013]Segment 李超线段树

    所谓李超线段树就是解决此题一类的问题(线段覆盖查询点最大(小)),把原本计算几何的题目变成了简单的线段树,巧妙地结合了线段树的标记永久化与标记下传,在不考虑精度误差的影响下,打法应该是这样的. #in ...

  8. bzoj 3165: [Heoi2013]Segment 线段树

    题目: Description 要求在平面直角坐标系下维护两个操作: 在平面上加入一条线段.记第i条被插入的线段的标号为i. 给定一个数k,询问与直线 x = k相交的线段中,交点最靠上的线段的编号. ...

  9. BZOJ 3165 李超线段树

    思路: 李超线段树 我是把线段转成斜率的形式搞得 不知道有没有更简单的方法 //By SiriusRen #include <cmath> #include <cstdio> ...

随机推荐

  1. cookie 跨域的问题

    今天研究一天发现cookie无法设置除当前域名或者其父域名之外的其他domain. 这个是浏览器出于对cookie的保护造成的,也就是cookie无法跨域设置. 对于子域名也有如下规则,当前域名只能设 ...

  2. python设计模式之迭代器与生成器详解(五)

    前言 迭代器是设计模式中的一种行为模式,它提供一种方法顺序访问一个聚合对象中各个元素, 而又不需暴露该对象的内部表示.python提倡使用生成器,生成器也是迭代器的一种. 系列文章 python设计模 ...

  3. 64_p7

    python-flask-whooshalchemy-0.6-10.fc26.noarch.rpm 12-Feb-2017 11:04 51894 python-flask-wtf-0.10.0-8. ...

  4. NOIP模拟赛 城市

    题目描述 $ZZQ$ 是一国之主. 这个国家有$N$个城市, 第$i$个城市与第$(i + 1) (mod N)$和$(i - 1) (mod N)$在一个正$N$边形相连. $ZZQ$ 又新建了$N ...

  5. Nginx源码分析--epoll模块

    Nginx采用epoll模块实现高并发的网络编程,现在对Nginx的epoll模块进行分析. 定义在src/event/modules/ngx_epoll_module.c中 1. epoll_cre ...

  6. MySQL 和 Oracle 主键自增长

    1.MySQL 1)建表 auto_increment:每插入一条数据,客户表(customers)的主键id就自动增1,如下所示 create table customers -- 创建客户表 ( ...

  7. laravel5.1--数据库操作

    1 配置信息 1.1配置目录: config/database.php 1.2配置多个数据库 //默认的数据库 'mysql' => [ 'driver' => 'mysql', 'hos ...

  8. 洛谷P2827 蚯蚓 题解

    洛谷P2827 蚯蚓 题解 题目描述 本题中,我们将用符号 ⌊c⌋ 表示对 c 向下取整. 蛐蛐国最近蚯蚓成灾了!隔壁跳蚤国的跳蚤也拿蚯蚓们没办法,蛐蛐国王只好去请神刀手来帮他们消灭蚯蚓. 蛐蛐国里现 ...

  9. 关于Android不同系统版本的市场占比情况详解

    一,google官方统计的不同Android版本市场的占比强开 google统计的数据情况 这个是google官方对于不同版本的市场占比情况.这个是针对全世界所有的Android手机占比情况. 二,友 ...

  10. ajax json 学习笔记

    json = { } JSON 字符串必须使用双引号,单引号会出现错误 三种类型: 简单值:字符串.数值.布尔值.null 对象:无序的键值对儿 数组:有序的值列表 解析:JSON.eval()   ...