zoukankan      html  css  js  c++  java
  • 2019南昌icpc网络赛 I题 二维偏序,分块套树状数组

    https://nanti.jisuanke.com/t/41356

    对于带修的二维数点,可以bit套主席树,也可CDQ三维偏序

    但是最后我选择分块套BIT暴力...

    复杂度为$m(blocksize+blocknum*logn)$

    显然,如果按照$sqrt{n}$分块,并不是最优的

    我们可以适当的增加块的大小,减少块的数量,让$blocksize=blocknum*logn$

    在这个题中,大概就是$sqrt{1e6}$到$sqrt{2e6}$之间吧

    #include<bits/stdc++.h>
    #define rep(ii,a,b) for(int ii=a;ii<=b;++ii)
    using namespace std;
    const int maxn=2e5+10,maxm=6e2+10;
    int n,m;
    namespace fastio{
    inline bool isdigit(char c){return c>=48&&c<=57;}
    const int maxsz=1e7;
    class fast_iostream{public:
      char ch=get_char();
      inline char get_char(){
        static char buffer[maxsz],*a=buffer,*b=buffer;
        return b==a&&(b=(a=buffer)+fread(buffer,1,maxsz, stdin),b==a)?EOF:*a++;
      }
      void operator>>(int& tmp){
        tmp=0;
        while(!isdigit(ch)&&ch!=EOF){ch=get_char();};
        if(ch==EOF)return ;
        do{tmp=ch-48+(tmp<<1)+(tmp<<3);}while(isdigit(ch=get_char()));
      }
    };
    int top;char stk[8];
    void put(int &tmp){
      if (!tmp){putchar('0');return;}
      top=0;
      while(tmp)stk[++top]=tmp%10+'0',tmp/=10;
      while(top)putchar(stk[top--]);
    }
    }fastio::fast_iostream io;
    class bit{public:
      int node[maxn];
      inline int lb(int x) {return x&(-x);}
      inline void update(int pos,int val){
        for(;pos<=n;pos+=lb(pos)) node[pos]+=val;
      }
      inline int ask(int pos){
        int sum=0;
        for(;pos>0;pos-=lb(pos)) sum+=node[pos];
        return sum;
      }
      inline int query(int l,int r){
        return ask(r)-ask(l-1);
      }
    };
    int aa[maxn],bb[maxn];
    class sqblock{public:
      struct block{
        int l,r;bit tree;
        void update(int pos,int val) {tree.update(pos,val);}
        int query(int l,int r) {return tree.query(l,r);}
      }node[maxm];
      int id[maxn],sz,cnt;
      void init(int n){
        sz=sqrt(2e6);
        rep(i,1,n) id[i]=(i-1)/sz+1;cnt=id[n];
        rep(i,1,cnt) node[i].l=(i-1)*sz+1;
        rep(i,1,cnt-1) node[i].r=i*sz;
        node[cnt].r=n;
        rep(i,1,n)if(aa[i]!=aa[i-1]) node[id[i]].update(aa[i],1);
      }
      void update(int x,int y){
        if(x>1&&aa[x]!=aa[x-1]) node[id[x]].update(aa[x],-1);
        if(x<n&&aa[x+1]!=aa[x]) node[id[x+1]].update(aa[x+1],-1);
        aa[x]=y;
        if(x>1&&aa[x]!=aa[x-1]) node[id[x]].update(aa[x],1);
        if(x<n&&aa[x+1]!=aa[x]) node[id[x+1]].update(aa[x+1],1);
      }
      int query(int l,int r,int x,int y){
        int posl=id[l],posr=id[r],ans=0;
        if(posl==posr) {
          rep(i,l,r) ans+=(aa[i]!=aa[i-1]&&aa[i]>=x&&aa[i]<=y);
          return ans;
        }
        rep(i,posl+1,posr-1) ans+=node[i].query(x,y);
        rep(i,l,node[posl].r) ans+=(aa[i]!=aa[i-1]&&aa[i]>=x&&aa[i]<=y);
        rep(i,node[posr].l,r) ans+=(aa[i]!=aa[i-1]&&aa[i]>=x&&aa[i]<=y);
        return ans;
      }
    }square;
    int x,y,b,c,d,e,a,ans;
    #define cin io
    int main() {
      cin>>n;cin>>m;
      rep(i,1,n) cin>>aa[i];
      square.init(n);
      while(m--){
        cin>>a;
        if(a==1){
          cin>>x;cin>>y;
          if(aa[x]!=y) square.update(x,y);
        }else {
          cin>>b;cin>>c;cin>>d;cin>>e;
          ans=square.query(b,c,d,e);
          if(aa[b]==aa[b-1]&&aa[b]>=d&&aa[b]<=e) ans++;
          fastio::put(ans);putchar('
    ');
        }
      }
    }
    
  • 相关阅读:
    安装Hadoop
    爬虫综合大作业
    爬取全部校园新闻
    理解爬虫原理
    中文词频统计与词云生成
    复合数据类型,英文词频统计
    字符串操作、文件操作,英文词频统计预处理
    了解大数据的特点、来源与数据呈现方式
    大数据应用期末总评
    分布式文件系统HDFS 练习
  • 原文地址:https://www.cnblogs.com/nervendnig/p/11498520.html
Copyright © 2011-2022 走看看