[主席树]SPOJ DQUERY

题目链接

题意:n个数 m个查询

查询的是[l, r]区间内不相同的数的个数

 

没有修改,因此静态的主席树就好了

将重复的元素建树即可

query的时候加起来,用区间长度(r-l+1)去减就是答案

(query的是[l, r]之间重复元素的个数)

 

[主席树]SPOJ DQUERY
  1 typedef long long LL;

  2 #define lson l, m

  3 #define rson m+1, r

  4 const int N=30005;

  5 int L[N<<5], R[N<<5], sum[N<<5];

  6 int tot;

  7 int a[N], T[N];

  8 int read()

  9 {

 10     char ch=' ';

 11     int ans=0;

 12     while(ch<'0' || ch>'9')

 13         ch=getchar();

 14     while(ch<='9' && ch>='0')

 15     {

 16         ans=ans*10+ch-'0';

 17         ch=getchar();

 18     }

 19     return ans;

 20 }

 21 

 22 int build(int l, int r)

 23 {

 24     int rt=(++tot);

 25     sum[rt]=0;

 26     if(l<r)

 27     {

 28         int m=(l+r)>>1;

 29         L[rt]=build(lson);

 30         R[rt]=build(rson);

 31     }

 32     return rt;

 33 }

 34 

 35 int update(int pre, int l, int r, int x)

 36 {

 37     int rt=(++tot);

 38     L[rt]=L[pre], R[rt]=R[pre], sum[rt]=sum[pre]+1;

 39     if(l<r)

 40     {

 41         int m=(l+r)>>1;

 42         if(x<=m)

 43             L[rt]=update(L[pre], lson, x);

 44         else

 45             R[rt]=update(R[pre], rson, x);

 46     }

 47     return rt;

 48 }

 49 

 50 int query(int u, int v, int l, int r, int k)

 51 {

 52      if(l>=k)

 53         return sum[v]-sum[u];

 54     int m=(l+r)>>1;

 55     int ans=0;

 56     if(m>=k)

 57         ans+=query(L[u], L[v], lson, k);

 58     ans+=query(R[u], R[v], rson, k);

 59     return ans;

 60 }

 61 

 62 int main()

 63 {

 64         tot=0;

 65         int n=read();

 66 //        scanf("%d", &n);

 67         for(int i=1; i<=n; i++)

 68         {

 69 //            scanf("%d", &a[i]);

 70             a[i]=read();

 71         }

 72         T[0]=0;

 73         map<int, int> mp;

 74         mp.clear();

 75         for(int i=1; i<=n; i++)

 76         {

 77             if(mp.find(a[i])!=mp.end())

 78                 T[i]=update(T[i-1], 1, n, mp[a[i]]);

 79             else

 80                 T[i]=T[i-1];

 81             mp[a[i]]=i;

 82         }

 83         int m=read();

 84 //        scanf("%d", &m);

 85         while(m--)

 86         {

 87             int l, r;

 88             l=read(), r=read();

 89 //            scanf("%d%d", &l, &r);

 90             printf("%d\n", r-l+1-query(T[l-1], T[r], 1, n, l));

 91         }

 92 }

 93 /*

 94 5

 95 1 1 2 1 3

 96 3

 97 1 5

 98 2 4

 99 3 5

100 */
SPOJ DQUERY

 

你可能感兴趣的:(query)