CF-19D Points (树套树)

来源:互联网 发布:人工智能杂志 编辑:程序博客网 时间:2024/04/28 21:54

题意: 给出一个二维平面,要求支持三种操作:插入一个点(x,y),删除一个点,以及查询横坐标比给定x大,纵坐标比给定y大的具有最小横坐标的点,输出它的坐标。如果有多个点具有相同x值,输出在满足要求下y值最小的那个。操作次数20W。

解法: 把所有的点离散化后按照y值排序,那么我们需要的答案就是在满足y的情况下找到最小的满足的x值。那么就使用树状数组来实现对y~正无穷这个区间的查询。

对y轴建树,把每个点插到它的y值对应的位置,用树状数组来维护。然后对于每次的询问点(x0,y0),查询y0+1~正无穷区间,在每个位置二分查找最小x值,最后维护一个最小值即为答案,复杂度n*(lgn)^2.

/* **********************************************Author      : NeroCreated Time: 2013/9/2 15:13:03Problem id  : CF-19DProblem Name: Points*********************************************** */#include <stdio.h>#include <string.h>#include <set>#include <algorithm>using namespace std;#define REP(i,a,b) for(int i=(a); i<(int)(b); i++)#define clr(a,b) memset(a,b,sizeof(a))typedef pair<int,int> P;#define MP make_pairconst int INF = 0x3f3f3f3f;const int MAXN = 201000;// 离散化struct San {    int a[MAXN], n;    int size() { return n; }    void init() { n = 0; }    void push(int x) { a[n++] = x; }    void doit() { sort(a,a+n); n = unique(a,a+n) - a; }    int operator [] (int x) { return lower_bound(a,a+n,x) - a; }}san;struct Query {    char c;    int x,y;}q[MAXN];int n;// 树状数组套setset <P> ss[MAXN];set <P> :: iterator it;inline void add(int p, P node) { for( ; p > 0; p -= p&-p) ss[p].insert(node); }inline void remove(int p, P node) { for( ; p > 0; p -= p&-p) ss[p].erase(node); }inline void query(int p, P node) {    P ans = MP(INF,INF);    for( ; p < san.size(); p += p&-p) {        it = ss[p].lower_bound(node);        if(it == ss[p].end()) continue;        ans = min(ans, *it);    }    if(ans.first == INF) printf("-1\n");    else printf("%d %d\n", ans.first, ans.second);}int main() {    scanf("%d", &n);    char s[10];    for(int i = 0; i < n ; i ++) {        scanf("%s%d%d", s, &q[i].x, &q[i].y);        q[i].c = s[0];        san.push(q[i].y);    }    san.doit();    for(int i = 0; i < n; i ++) {        if(q[i].c == 'a') add(san[q[i].y], MP(q[i].x,q[i].y));        else if(q[i].c == 'r') remove(san[q[i].y], MP(q[i].x, q[i].y));        else query(san[q[i].y]+1, MP(q[i].x+1, q[i].y+1));    }    return 0;}


原创粉丝点击