Pete and Bob invented a new interesting game. Bob takes a sheet of paper and locates a Cartesian coordinate system on it as follows: point (0, 0) is located in the bottom-left corner, Ox axis is directed right, Oy axis is directed up. Pete gives Bob requests of three types:

  • add x y — on the sheet of paper Bob marks a point with coordinates (x, y). For each request of this type it's guaranteed that point (x, y) is not yet marked on Bob's sheet at the time of the request.
  • remove x y — on the sheet of paper Bob erases the previously marked point with coordinates (x, y). For each request of this type it's guaranteed that point (x, y) is already marked on Bob's sheet at the time of the request.
  • find x y — on the sheet of paper Bob finds all the marked points, lying strictly above and strictly to the right of point (x, y). Among these points Bob chooses the leftmost one, if it is not unique, he chooses the bottommost one, and gives its coordinates to Pete.

Bob managed to answer the requests, when they were 10, 100 or 1000, but when their amount grew up to 2·105, Bob failed to cope. Now he needs a program that will answer all Pete's requests. Help Bob, please!

Input

The first input line contains number n (1 ≤ n ≤ 2·105) — amount of requests. Then there follow n lines — descriptions of the requests. add x y describes the request to add a point, remove x y — the request to erase a point, find x y — the request to find the bottom-left point. All the coordinates in the input file are non-negative and don't exceed 109.

Output

For each request of type find x y output in a separate line the answer to it — coordinates of the bottommost among the leftmost marked points, lying strictly above and to the right of point (x, y). If there are no points strictly above and to the right of point (x, y), output -1.

Example

Input
7
add 1 1
add 3 4
find 0 0
remove 1 1
find 0 0
add 1 1
find 0 0
Output
1 1
3 4
1 1
Input
13
add 5 5
add 5 6
add 5 7
add 6 5
add 6 6
add 6 7
add 7 5
add 7 6
add 7 7
find 6 6
remove 7 7
find 6 6
find 4 4
Output
7 7
-1
5 5

题意:给定二维平面,有Q个操作。对于每个操作,输入Opt,X,Y。

如果Opt==“add”,则加(X,Y)。

如果Opt==“remove”,则删去(X,Y)

否则,查找(X,Y)右上方最靠左的点,若果有多个,取Y最小,输出坐标。

思路:离散化,对X轴建立线段树,树节点保存子树的最大Y坐标值Max。利用线段树查找的思想相当于是分治吧,即,在查找(X,Y)右上方点时,只要找到X的右边部分的线段树里第一个Max>Y,得到X’,然后set二分得到Y‘就ok。

(为了统一,我新习惯把单点也看成区间。)

#include<set>
#include<cstdio>
#include<cstdlib>
#include<iostream>
#include<algorithm>
using namespace std;
const int maxn=;
int x[maxn],y[maxn],opt[maxn],a[maxn];
char chr[]; set<int>s[maxn];
void read(int &res){
char c=getchar(); for(;c>''||c<'';c=getchar());
for(res=;c>=''&&c<='';c=getchar()) res=(res<<)+(res<<)+c-'';
}
int Max[maxn<<],ans,ht;
struct segment_tree
{
void add(int Now,int L,int R,int l,int r,int Y)
{
if(l<=L&&r>=R){
s[l].insert(Y);
Max[Now]=*(s[l].rbegin());
return ;
}
int Mid=(L+R)>>;
if(l<=Mid) add(Now<<,L,Mid,l,r,Y);
if(r>Mid) add(Now<<|,Mid+,R,l,r,Y);
Max[Now]=max(Max[Now<<],Max[Now<<|]);
}
void del(int Now,int L,int R,int l,int r,int Y)
{
if(l<=L&&r>=R){
s[l].erase(Y);
if(s[l].empty()) Max[Now]=-;
else Max[Now]=*(s[l].rbegin());
return ;
}
int Mid=(L+R)>>;
if(l<=Mid) del(Now<<,L,Mid,l,r,Y);
if(r>Mid) del(Now<<|,Mid+,R,l,r,Y);
Max[Now]=max(Max[Now<<],Max[Now<<|]);
}
void find(int Now,int L,int R,int l,int r,int Y)
{
if(Max[Now]<=Y) return ;
if(l<=L&&r>=R){
if(L==R){
ans=L; ht=*(s[L].upper_bound(Y));
return ;
}
int Mid=(L+R)>>;
find(Now<<,L,Mid,l,r,Y);
if(ans==-) find(Now<<|,Mid+,R,l,r,Y);
return ;
}
int Mid=(L+R)>>;
if(l<=Mid) find(Now<<,L,Mid,l,r,Y);
if(ans==-&&r>Mid) find(Now<<|,Mid+,R,l,r,Y);
}
}Tree;
int main()
{
int N,M;
read(N);
for(int i=;i<=N;i++){
scanf("%s",chr); read(x[i]); read(y[i]);
if(chr[]=='r') opt[i]=-;
if(chr[]=='a') opt[i]=;
if(chr[]=='f') opt[i]=;
a[i]=x[i];
}
sort(a+,a+N+);
M=unique(a+,a+N+)-(a+);
for(int i=;i<=N;i++){
int X=lower_bound(a+,a+M+,x[i])-a;
if(opt[i]==) Tree.add(,,M,X,X,y[i]);
else if(opt[i]==-) Tree.del(,,M,X,X,y[i]);
else{
ans=ht=-;
Tree.find(,,M,X+,M,y[i]);
if(ans==-) printf("-1\n");
else printf("%d %d\n",a[ans],ht);
}
}
return ;
}

CodeForces19D:Points(线段树+set(动态查找每个点右上方的点))的更多相关文章

  1. [Codeforces19D]Points 线段树

    大致题意: 给出n个询问,每次询问有三种: 1.往平面上加一个点 2.删除平面上的一个点 3.给出一个点p,查询平面上某点q,使得q.x>p.x且q.y>p.y,输出x轴坐标最小的q,若有 ...

  2. 【xsy3423】党² 线段树+李超线段树or动态半平面交

    本来并不打算出原创题的,此题集CF542A和sk的灵感而成,算个半原创吧. 题目大意: 给定有$n$个元素的集合$P$,其中第$i$个元素中包含$L_i,R_i,V_i$三个值. 给定另一个有$n$个 ...

  3. HDU 5877 2016大连网络赛 Weak Pair(树状数组,线段树,动态开点,启发式合并,可持久化线段树)

    Weak Pair Time Limit: 4000/2000 MS (Java/Others)    Memory Limit: 262144/262144 K (Java/Others) Tota ...

  4. CodeForces 19D Points (线段树+set)

    D. Points time limit per test 2 seconds memory limit per test 256 megabytes input standard input out ...

  5. Codeforces 1140F Extending Set of Points 线段树 + 按秩合并并查集 (看题解)

    Extending Set of Points 我们能发现, 如果把x轴y轴看成点, 那么答案就是在各个连通块里面的x轴的个数乘以y轴的个数之和. 然后就变成了一个并查集的问题, 但是这个题目里面有撤 ...

  6. BZOJ.4553.[HEOI2016&TJOI2016]序列(DP 树状数组套线段树/二维线段树(MLE) 动态开点)

    题目链接:BZOJ 洛谷 \(O(n^2)\)DP很好写,对于当前的i从之前满足条件的j中选一个最大值,\(dp[i]=d[j]+1\) for(int j=1; j<i; ++j) if(a[ ...

  7. [hdu4347]The Closest M Points(线段树形式kd-tree)

    解题关键:kdtree模板题,距离某点最近的m个点. #include<cstdio> #include<cstring> #include<algorithm> ...

  8. bzoj2212 Tree Rotations 线段树合并+动态开点

    题目传送门 思路: 区间合并线段树的题,第一次写,对于一颗子树,无论这个子树怎么交换,都不会对其他子树的逆序对造成影响,所以就直接算逆序对就好. 注意叶子节点是1到n的全排列,所以每个权值都只会出现1 ...

  9. kb-07线段树-12--二分查找区间边界

    /* hdu4614 本题刚开始想能不能记录该区间最前面开始的点,最后面的点,区间空的数量:但是病不行 然后线段树的本质是区间操作,所以!这题主要就是区间的空的全放满,只要定出区间的边界就好办了: 这 ...

随机推荐

  1. Spring Task Schedule 及多线程

    http://spring.io/blog/2010/01/05/task-scheduling-simplifications-in-spring-3-0/‘ http://ekramalikazi ...

  2. HDU 1394 线段树求逆序对

    Minimum Inversion Number Time Limit: 2000/1000 MS (Java/Others)    Memory Limit: 65536/32768 K (Java ...

  3. Ubuntu 16.04安装JAD反编译工具(Java)

    JAD反编译工具有个好处,就是字节码和源代码一起输出. 官网:https://varaneckas.com/jad/ 安装步骤: 1.下载: 离线版本:(链接: https://pan.baidu.c ...

  4. jquery ajax 跨域訪问样例

    <script type="text/javascript"> $(function(){    $.ajax({    cache : false,    type ...

  5. Mathematica 表达式求值

    表达式是变量之间的运算关系.表达式求值就是对变量赋值并运算出结果的过程. 针对于Mathematica中的表达式.有两种方法获得其值. 一是对对应的变量直接赋值.这样对应的表达式在调用时便会直接运算得 ...

  6. Solidworks如何绘制装饰螺纹线

    1 插入-注解,装饰螺纹线   2 绘制装饰螺纹线,选择螺纹的边线,标准选择ISO,下面可以选择的范围就确定了(M6的孔,只能选择M8的螺纹或者M10的螺纹),画好之后在3D图中并没有明确的螺纹样式 ...

  7. android 自己定义控件

    Android自己定义View实现非常easy 继承View,重写构造函数.onDraw.(onMeasure)等函数. 假设自己定义的View须要有自己定义的属性.须要在values下建立attrs ...

  8. php新版本号废弃 preg_replace /e 修饰符

    近期serverphp版本号升级到了 5.6  发现出了非常多警告 preg_replace(): The /e modifier is deprecated, use preg_replace_ca ...

  9. BEGINNING SHAREPOINT&#174; 2013 DEVELOPMENT 第8章节--配送SP2013Apps 应用程序生命周期

    BEGINNING SHAREPOINT® 2013 DEVELOPMENT 第8章节--配送SP2013Apps 应用程序生命周期         你在商店拥有一个应用程序后.跟踪不论什么人们碰到的 ...

  10. python day-3 基本数据类型

    1. 编码 1. 最早的计算机编码是ASCII. 美国人创建的. 包含了英文字母(大写字母, 小写字母). 数字, 标点等特殊字符!@#$% 128个码位 2**7 在此基础上加了一位 2**8 8位 ...