zoukankan      html  css  js  c++  java
  • cf104G AI robots

    传送门
    很有限制的一道题
    对于任意机器人,存在一个初始位置点和一个观测半径以及iq值
    任意两个机器人,如果都能观测到对方且iq值差距不大于k,那么可以进行交流。求交流的机器人有几对。

    每个人有2个属性,可以想到是CDQ分治。
    然后对于观测来说,只需要按照观测半径先进行排序,那么在CDQ分治里面,你去找到一个点时,这个点能观测到之前的点,那么之前的点肯定也能观测到这个点。
    那么接下来就处理半径问题和iq问题。

    我们考虑在CDQ分治里的排序。我们用iq进行排序,位置用树状数组维护。
    因为考虑到有限制,即([mid + 1, r])上的点要去找iq值都符合的点,因为iq值是在CDQ分治里排序的,那么也就是说对于这个区间里的点对应的最小iq值下标和最大iq值下标是单调的,也就是说随着我iq值的增加,查询谁能匹配的那个区间是单调的,向右增加的,但都在([l, mid])里,那么就考虑用单调队列的思想去搞。找到两个区间就行了。
    而在找的过程,同时维护下树状数组,把点的坐标加进去。
    最后查询时就是看我的观测区间里面有多少个点就行了。

    对于有限制的区间,可以先想想这个区间是否的单调递增,即l,r只能向右边移动的,然后用单调队列思想。
    CQD应该考虑维度多少,属性有什么,以及第一维度按照什么进行排序,第二维度按照上面进行排序,第三维度维护什么之类的。
    然后要注意的是第三维度即树状数组维护的值都要离散化的。

    #include <bits/stdc++.h>
    using namespace std;
    int n, k;
    template<typename T = long long> inline T read() {
        T s = 0, f = 1; char ch = getchar();
        while(!isdigit(ch)) {if(ch == '-') f = -1; ch = getchar();}
        while(isdigit(ch)) {s = (s << 3) + (s << 1) + ch - 48; ch = getchar();} 
        return s * f;
    }
    const int N = 4e5 + 5, M = 1e6 + 5, MOD = 1e9 + 7, CM = 998244353, INF = 0x3f3f3f3f;
    int b[N];
    struct Operation{
        int x, rr, iq, l, r;
    } q[N];
    struct BIT{
        int c[N];
        int lowbit(int x) {return x & (-x);}
        void add(int pos, int val) {for(; pos < N; pos += lowbit(pos)) c[pos] += val;}
        int sum(int pos) { int res = 0; for(; pos; pos -= lowbit(pos)) res += c[pos]; return res;}
        int query(int l, int r) {return sum(r) - sum(l - 1);}
        void clear(int pos) {for(; pos < N; pos += lowbit(pos)) c[pos] = 0;}
    } bit;
    long long ans = 0;
    void CDQ(int l, int r){
        if(l == r) return;
        int mid = (l + r) >> 1;
        CDQ(l, mid), CDQ(mid + 1, r);
        int lp = l, rp = l;
        for(int i = mid + 1; i <= r; i++) { // 贡献在[mid + 1, r]
            while(lp <= mid && q[lp].iq < q[i].iq - k) bit.add(q[lp++].x, -1);
            while(rp <= mid && q[rp].iq <= q[i].iq + k) bit.add(q[rp++].x, 1);
            ans += bit.query(q[i].l, q[i].r);
        }
        for(int i = lp; i < rp; i++) bit.add(q[i].x, -1);
        sort(q + l, q + r + 1, [](Operation &a, Operation &b){
            return a.iq < b.iq;
        }); 
    }
    int all_num = 0;
    int main(){
        n = read(), k = read();
        for(int i = 1; i <= n; i++) {
            int x = read(), r = read(), iq = read();
            q[i] = Operation{x, r, iq, 0, 0};
            b[++all_num] = x;
            b[++all_num] = x - r;
            b[++all_num] = x + r;
        }
        sort(b + 1, b + all_num + 1);
        int qq = unique(b + 1, b + all_num + 1) - b - 1;
        for(int i = 1; i <= n; i++) {
            q[i].l = lower_bound(b + 1, b + qq + 1, q[i].x - q[i].rr) - b;
            q[i].r = lower_bound(b + 1, b + qq + 1, q[i].x + q[i].rr) - b;
            q[i].x = lower_bound(b + 1, b + qq + 1, q[i].x) - b;
        }
        sort(q + 1, q + n + 1, [](Operation &a, Operation &b){
            return a.rr > b.rr;
        });
        CDQ(1, n);
        printf("%lld
    ", ans);
        return 0;
    }
    
    I‘m Stein, welcome to my blog
  • 相关阅读:
    JDBI
    Concise: Compressed ’n’ Composable Integer Set
    java 7 新特性
    BIO的简单Demo
    手写一个死锁Demo
    实现一个Cglib代理Demo
    实现一个JDK代理demo
    ClassNotFoundException和 NoClassDefFoundError区别验证
    集合—ArrayList
    Hadoop之Storm基础
  • 原文地址:https://www.cnblogs.com/Emcikem/p/14360930.html
Copyright © 2011-2022 走看看