zoukankan      html  css  js  c++  java
  • HDU 4866 Shooting (主席树)

    题目链接  HDU 4866

    题意  给定$n$条线段。每条线段平行$x$轴,离x轴的距离为$D$,覆盖的坐标范围为$[L, R]$。

        现在有$m$次射击行动,每一次的射击行动可以描述为在横坐标$x$处找到离$x$轴最近的$k$条线段,

        并计算这$k$个目标距离$x$轴的总和。强制在线。

     

    对线段到$x$轴的距离离散化。 以横坐标为下标建立主席树。

    应用差分思想,对于每条线段,在$L$处标记$+1$,在$R+1$处标记$-1$,

    查询的时候在横坐标$x$处则查找横坐标$x$对应的主席树即可。

    主席树维护两个东西:

    $s[]$表示当前维护的区间范围内的权值和。

    $t[]$表示当前维护的区间范围内的权值个数。

    对于那点右端点很坐标小于$x$的线段,在之前的两次插入操作中正负抵消。

    于是就保证了查询到的线段横坐标范围覆盖了当前的$x$。

    #include <bits/stdc++.h>
    
    using namespace std;
    
    #define rep(i, a, b)	for (int i(a); i <= (b); ++i)
    #define dec(i, a, b)	for (int i(a); i >= (b); --i)
    
    typedef long long LL;
    
    const int M = 4e6 + 10;
    const int N = 2e5 + 10;
    
    struct node{
    	int pos, val, num;
    	friend bool operator < (const node &a, const node &b){
    		return a.pos == b.pos ? (a.val == b.val ? a.num < b.num : a.val < b.val) : (a.pos < b.pos);
    	}
    } c[M], nd;
    
    int ls[M], rs[M], tree[N], val[N], t[M], tot;
    int cnt, now, k, x, m, n, et, p;
    LL  s[M], pre, ans;
    
    void ins(int l, int r, int vl, int fl, int pre, int &x){
    	x = ++tot;
    	ls[x] = ls[pre];
    	rs[x] = rs[pre];
    
    	s[x] = s[pre] + fl * val[vl];
    	t[x] = t[pre] + fl;
    
    	if (l == r) return;
    
    	int mid = (l + r) >> 1;
    	if (vl <= mid) ins(l, mid, vl, fl, ls[pre], ls[x]);
    	else ins(mid + 1, r, vl, fl, rs[pre], rs[x]);
    }
    
    LL query(int id, int l, int r, int k){
    	if (l == r) return 1ll * k * val[l];
    
    	int mid = (l + r) >> 1;
    
    	if (t[ls[id]] > k) return query(ls[id], l, mid, k);
    	else if (t[ls[id]] == k) return s[ls[id]];
    	else return s[ls[id]] + query(rs[id], mid + 1, r, k - t[ls[id]]);
    }
    
    int main(){
    
    	while (~scanf("%d%d%d%d", &n, &m, &x, &p)){
    		et = 0;
    		rep(i, 1, n){
    			int l, r, d;
    			scanf("%d%d%d", &l, &r, &d);
    			val[i] = d;
    			++et;
    			c[et].pos = l;
    			c[et].val = d;
    			c[et].num = 1;
    			++et;
    			c[et].pos = r + 1;
    			c[et].val = d;
    			c[et].num = -1;
    		}
    
    		sort(val + 1, val + n + 1);
    		cnt = unique(val + 1, val + n + 1) - val - 1;
    
    		now = 0;
    
    		rep(i, 1, n << 1) c[i].val = lower_bound(val + 1, val + cnt + 1, c[i].val) - val;
    		sort(c + 1, c + 2 * n + 1);
    		tree[0] = ls[0] = rs[0] = s[0] = t[0] = tot = 0;
    
    		pre = 1;
    		now = 0;
    
    		rep(i, 1, 2 * n) ins(1, cnt, c[i].val, c[i].num, tree[i - 1], tree[i]);
    		rep(i, 1, m){
    			LL pos, a, b, cc;
    			scanf("%lld%lld%lld%lld", &pos, &a, &b, &cc);
    			k = (a * pre + b) % cc;
    
    			nd.pos = pos;
    			nd.val = 1e9;
    
    			int y = upper_bound(c + 1, c + 2 * n + 1, nd) - c - 1;
    			ans = query(tree[y], 1, cnt, k);
    
    			if (pre > p) ans *= 2;
    			pre = ans;
    
    			printf("%lld
    ", ans);
    		}
    
    	}
    	return 0;
    }
    

      

  • 相关阅读:
    虚函数和纯虚函数
    MS CRM 2011中PartyList类型字段的实例化
    MS CRM 2011的自定义与开发(12)——表单脚本扩展开发(4)
    MS CRM 2011的自定义与开发(12)——表单脚本扩展开发(2)
    MS CRM 2011的自定义和开发(10)——CRM web服务介绍(第二部分)——IOrganizationService(二)
    MS CRM 2011 SDK 5.08已经发布
    MS CRM 2011 Q2的一些更新
    最近很忙
    Microsoft Dynamics CRM 2011最近的一些更新
    补一篇,Update Rollup 12 终于发布了
  • 原文地址:https://www.cnblogs.com/cxhscst2/p/8387690.html
Copyright © 2011-2022 走看看