【树状数组】 HDU 5372 Segment Game

点击打开链接

题意:

两种操作 :a,b

a=0:插入一个区间 长度为num 区间范围为[b,b+num] ( num表示为 这条区间的编号  第一个插入的 num=1,第二个插入的 num = 2

a=1:删除第b个区间

插入一个线段 要输出 在这个区间内的区间数量

维护线段左右两端的位置数量   ( 输出 大于等于左端点的数量 减去  大于右端点的数量)

所有的区间分成6种 容斥下就好了

#include <stdio.h>
#include <string.h>
#include <stdlib.h>
#include <math.h>
#include <string>
#include <iostream>
#include <algorithm>
using namespace std;
#include <queue>
#include <stack>
#include <vector>
#include <deque>
#include <set>
#pragma comment(linker, "/STACK:1024000000,1024000000")
#include <map>
typedef long long LL;
#define lson l,m,rt<<1
#define rson m+1,r,rt<<1|1
const int MAXN = 410000;//点数的最大值
const int MAXM = 604000;//边数的最大值
const LL INF = 1152921504;
const LL mod= 1e9+7;
int c[MAXN][2],all;
int lowbit(int x)
{
    return x&(-x);
}
int sum(int p,int num)
{
    int ans=0;
    while(p>0)
    {
        ans+=c[p][num];
        p-=lowbit(p);
    }
    return ans;
}
int add(int p,int val,int num)
{
    while(p<=all)
    {
        c[p][num]+=val;
        p+=lowbit(p);
    }
}
int a[MAXN],b[MAXN],d[MAXN],to[MAXN];
int main()
{
    int n,cas=1;
    while(scanf("%d",&n)!=EOF)
    {
        printf("Case #%d:\n",cas++);
        int a0=1;
        all=0;
        for(int i=0;i<n;i++)
        {
            scanf("%d%d",&a[i],&b[i]);
            if(a[i]==0)
            {
                d[all++]=b[i];
                d[all++]=b[i]+a0;
                to[a0++]=i;
            }
        }
        sort(d,d+all);
        all=unique(d,d+all)-d;
        memset(c,0,sizeof(c));
        a0=1;
        for(int i=0;i<n;i++)
        {
            if(a[i]==0)
            {
                int x=lower_bound(d,d+all,b[i])-d+1;
                int y=lower_bound(d,d+all,b[i]+a0)-d+1;
                int ans1=sum(all,0)-sum(x-1,0);
                int ans2=sum(all,1)-sum(y,1);
                cout<<ans1-ans2<<endl;
                a0++;
                add(x,1,0);
                add(y,1,1);
            }
            else
            {
                int x=lower_bound(d,d+all,b[to[b[i]]])-d+1;
                int y=lower_bound(d,d+all,b[to[b[i]]]+b[i])-d+1;
                add(x,-1,0);
                add(y,-1,1);
            }
        }
    }
    return 0;
}
/*
*/


發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章