2019南昌网络赛-I. Yukino With Subinterval 线段树套树状数组

时间:2019-09-13
本文章向大家介绍2019南昌网络赛-I. Yukino With Subinterval 线段树套树状数组,主要包括2019南昌网络赛-I. Yukino With Subinterval 线段树套树状数组使用实例、应用技巧、基本知识点总结和需要注意事项,具有一定的参考价值,需要的朋友可以参考一下。

TMD。。。这题卡内存卡的真优秀。。。

所以以后还是别用主席树的写法。。。不然怎么死的都不知道。。。

树套树中,主席树方法开权值线段树。。。会造成空间的浪费。。。这道题内存卡的很紧。。。

由于树套树已经不需要持久化了,直接动态开点就完事了。。。用主席树方法开过不去,要么超内存,要么越界。。。

大概思路。。。留坑。。。

#include<iostream>
#include<stdio.h>
#include<string.h>
#include<algorithm>
using namespace std;
const int maxx = 2e5+6;
struct node{
   int l,r;
   int cnt;
}tree[maxx*220];
int cnt,n,cnt1,cnt2;
int root[maxx],a[maxx],trl[maxx],trr[maxx];
void inserts(int &now,int l,int r,int pos,int w){
   if(!now)now=++cnt;
   tree[now].cnt+=w;
   if (l==r){
    return ;
   }
   int mid=(l+r)>>1;
   if (pos<=mid){
    inserts(tree[now].l,l,mid,pos,w);
   }else{
    inserts(tree[now].r,mid+1,r,pos,w);
   }
}
int lowbit(int x){
   return x&(-x);
}
void add(int x,int w){
   for(int i=x;i<=n;i+=lowbit(i)){
       inserts(root[i],1,n,a[x],w);
   }
}
int query(int l,int r,int ql,int qr){
    if (r<ql || l>qr){
        return 0;
    }
    int tmpl[1000],tmpr[1000];
    int s=0,mid=(l+r)>>1,sum=0;
    for(int i=1;i<=cnt1;i++)s-=tree[trl[i]].cnt,tmpl[i]=trl[i];
    for(int i=1;i<=cnt2;i++)s+=tree[trr[i]].cnt,tmpr[i]=trr[i];
    if (ql<=l && r<=qr){
         return s;
    }
    if (mid>=ql){
        for (int i=1;i<=cnt1;i++){
            trl[i]=tree[tmpl[i]].l;
        }
        for (int i=1;i<=cnt2;i++){
            trr[i]=tree[tmpr[i]].l;
        }
        sum+=query(l,mid,ql,qr);
    }
    if (mid<qr){
        for (int i=1;i<=cnt1;i++){
            trl[i]=tree[tmpl[i]].r;
        }
        for (int i=1;i<=cnt2;i++){
            trr[i]=tree[tmpr[i]].r;
        }
        sum+=query(mid+1,r,ql,qr);
    }
    return sum;
}
int main(){
  int m;
  scanf("%d%d",&n,&m);
    cnt=cnt1=cnt2=0;
  for (int i=1;i<=n;i++){
    scanf("%d",&a[i]);
    if (a[i]!=a[i-1])add(i,1);
  }
  int op;
  int pos,v,l,r,x,y;
  while(m--){
    scanf("%d",&op);
    if(op==1){
        scanf("%d%d",&pos,&v);
        if (a[pos]==v)continue;
        if(a[pos]!=a[pos-1]){
            add(pos,-1);
        }
        if(a[pos]==a[pos+1]){
            add(pos+1,1);
        }else if (a[pos+1]==v){
            add(pos+1,-1);
        }
        a[pos]=v;
        if (a[pos]!=a[pos-1]){
            add(pos,1);
        }
    }else {
        scanf("%d%d%d%d",&l,&r,&x,&y);
        cnt1=cnt2=0;
        int f=0;
        for (int i=l;i;i-=lowbit(i)){
            trl[++cnt1]=root[i];
        }
        for (int i=r;i;i-=lowbit(i)){
            trr[++cnt2]=root[i];
        }
        if (a[l]>=x && a[l]<=y)f++;
        printf("%d\n",query(1,n,x,y)+f);
    }
  }
  return 0;
}

原文地址:https://www.cnblogs.com/bluefly-hrbust/p/11516694.html