zoukankan      html  css  js  c++  java
  • 【习题整理】分块+莫队(未完待续)

    注意:这是一篇十分劣质的博客,只有题目和简单的几句话,慎用。。。。。。。。。。OVO

    分块

    入门推荐:http://hzwer.com/8053.html

    bzoj2957

            这个题有线段树和分块两种做法;

           线段树维护了区间的答案合并的时候维护高度最大值,右区的左子区间进一步讨论对分类讨论;

           分块就对每个块维护一个可看到的上升序列,lower_bound即可;

     1 #include<bits/stdc++.h>
     2 #define ll long long
     3 #define il inline 
     4 #define rg register  
     5 using namespace std;
     6 const int N=100010,M=610;
     7 int n,m,bl[N],u,t[M],len;
     8 double a[N],g[M][M]; 
     9 il int find(int i,double x){
    10     int l=1,r=t[i]+1;
    11     while(l<r){
    12         int mid=(l+r)>>1;
    13         if(x<g[i][mid])r=mid;
    14         else l=mid+1;
    15     }
    16     return l;
    17 }
    18 il void update(int x){
    19     int l=(bl[x]-1)*u+1,r=bl[x]*u;
    20     t[bl[x]]=0;
    21     for(rg int i=l;i<=r;i++)
    22     if(g[bl[x]][t[bl[x]]]<a[i])g[bl[x]][++t[bl[x]]]=a[i];
    23     double mx=0; int ans=0;
    24     for(rg int i=1;i<=len;i++){
    25         int p = find(i,mx);
    26         ans += t[i]-p+1; 
    27         if(mx<g[i][t[i]])mx=g[i][t[i]];
    28     }
    29     printf("%d
    ",ans);
    30 }
    31 il char gc(){
    32     static char *p1,*p2,s[1000000];
    33     if(p1==p2)p2=(p1=s)+fread(s,1,1000000,stdin);
    34     return(p1==p2)?EOF:*p1++; 
    35 } 
    36 il int rd(){
    37     int x=0; char c=gc();
    38     while(c<'0'||c>'9')c=gc();
    39     while(c>='0'&&c<='9')x=(x<<1)+(x<<3)+c-'0',c=gc();
    40     return x;
    41 }
    42 int main(){
    43 //    freopen("bzoj2957.in","r",stdin);
    44 //    freopen("bzoj2957.out","w",stdout);
    45     n=rd(); m=rd();
    46     u=550;
    47     for(rg int i=1;i<=n;i++)bl[i]=(i-1)/u+1;
    48     len=bl[n];
    49     for(rg int i=1;i<=n;i++)a[i]=-1;
    50     for(rg int i=1,x,y;i<=m;i++){
    51         x=rd(),y=rd();
    52         a[x]=1.0*y/x;
    53         update(x);
    54     }
    55     return 0;
    56 }
    bzoj2957


    bzoj2141

            交换两个位置,维护逆序对;

            考虑两个位置的影响,对每个块维护一个树状数组;

     1 #include<bits/stdc++.h>
     2 #define rg register 
     3 #define il inline 
     4 #define ll long long 
     5 using namespace std;
     6 const int N=20010,M=810;
     7 int n,m,c[M][N],a[N],sub[N],tot,sz[N],bl[N],u,len;
     8 ll ans;
     9 il char gc(){
    10     static char*p1,*p2,s[1000000];
    11     if(p1==p2)p2=(p1=s)+fread(s,1,1000000,stdin);
    12     return(p1==p2)?EOF:*p1++;
    13 }
    14 il int rd(){
    15     int x=0; char C=gc();
    16     while(C<'0'||C>'9')C=gc();
    17     while(C>='0'&&C<='9')x=(x<<1)+(x<<3)+C-'0',C=gc();
    18     return x;
    19 }
    20 il void add(int id,int x,int y){for(rg int i=x;i<=tot;i+=i&-i)c[id][i]+=y;}
    21 il int query(int id,int x){int re=0;for(rg int i=x;i;i-=i&-i)re+=c[id][i];return re;}
    22 void update(int x,int y){
    23     int tx=a[x],ty=a[y];
    24     add(bl[x],a[x],-1);
    25     add(bl[y],a[y],-1);
    26     swap(a[x],a[y]);
    27     add(bl[x],a[x],1);
    28     add(bl[y],a[y],1);
    29     if(tx>ty)ans--;else if(tx<ty)ans++; else return;
    30     if((++x)>(--y))return ;
    31     if(bl[x]==bl[y]){
    32         for(rg int i=x;i<=y;i++){
    33             if(tx<a[i])ans++;else if(tx>a[i])ans--;
    34             if(ty>a[i])ans++;else if(ty<a[i])ans--;  
    35         }
    36     }else{
    37         int t=bl[x]*u;for(rg int i=x;i<=t;i++){
    38             if(tx<a[i])ans++;else if(tx>a[i])ans--;
    39             if(ty>a[i])ans++;else if(ty<a[i])ans--;  
    40         }
    41         t=(bl[y]-1)*u+1;for(rg int i=t;i<=y;i++){
    42             if(tx<a[i])ans++;else if(tx>a[i])ans--;
    43             if(ty>a[i])ans++;else if(ty<a[i])ans--;  
    44         }
    45         for(rg int i=bl[x]+1;i<bl[y];i++){
    46             ans -= query(i,tx-1);
    47             ans += sz[i] - query(i,tx);
    48             ans -= sz[i] - query(i,ty);
    49             ans += query(i,ty-1);
    50         }
    51     }
    52 } 
    53 int main(){
    54 //    freopen("bzoj2141.in","r",stdin);
    55 //    freopen("bzoj2141.out","w",stdout);
    56     n=rd();
    57     for(rg int i=1;i<=n;i++)a[i]=sub[i]=rd();
    58     sort(sub+1,sub+n+1);
    59     tot=unique(sub+1,sub+n+1)-sub-1;
    60     u=pow(n,0.6666666)/*sqrt(n)*/ , len=(n-1)/u+1;
    61     for(rg int i=n;i;i--){
    62         a[i]=lower_bound(sub+1,sub+tot+1,a[i])-sub;
    63         bl[i]=(i-1)/u+1;
    64         if(bl[i]==bl[i-1])sz[i]=sz[i-1]+1;else sz[i]=1;
    65         add(bl[i],a[i],1);
    66         ans += query(0,a[i]-1);
    67         add(0,a[i],1);
    68     }
    69     printf("%lld
    ",ans);
    70     m=rd();
    71     for(rg int i=1;i<=m;i++){
    72         int x=rd(),y=rd();
    73         if(x>y)swap(x,y);
    74         update(x,y);
    75         printf("%lld
    ",ans); 
    76     }
    77     return 0;
    78 } 
    bzoj2141


    bzoj3744

           其实也一样,只不过多个套路维护每个块的前缀和就可以快速查询整块了(我没码。。。。。)

    bzoj2821

          也是套路,维护d[i][j]表示块i到块j的答案,然后再记录出现次数的前缀和,用讨论散块对答案的影响;

     1 #include<bits/stdc++.h>
     2 #define rg register 
     3 #define il inline 
     4 using namespace std;
     5 const int N=100010,M=320;
     6 int n,m,q,c[M][N],d[M][M],tmp[N],bl[N],a[N],u,len,st[M],ed[M];
     7 il char gc(){
     8     static char*p1,*p2,s[1000000];
     9     if(p1==p2)p2=(p1=s)+fread(s,1,1000000,stdin);
    10     return(p1==p2)?EOF:*p1++;
    11 }
    12 il int rd(){
    13     int x=0; char ch=gc();
    14     while(ch<'0'||ch>'9')ch=gc();
    15     while(ch>='0'&&ch<='9')x=(x<<1)+(x<<3)+ch-'0',ch=gc();
    16     return x;
    17 }
    18 il int query(int x,int y){
    19     int re=0,num;
    20     if(bl[x]==bl[y]){
    21         for(rg int i=x;i<=y;i++){
    22             if(++tmp[a[i]]==1)continue;
    23             if(tmp[a[i]]&1)re--;else re++;
    24         }
    25         for(rg int i=x;i<=y;i++)tmp[a[i]]=0;
    26     }else{
    27         if(bl[x]+1<bl[y])re=d[bl[x]+1][bl[y]-1];
    28         for(rg int i=x;i<=ed[bl[x]];i++){
    29             num = c[bl[y]-1][a[i]] - c[bl[x]][a[i]]  + (++tmp[a[i]]); 
    30             if(num==1)continue;
    31             if(num&1)re--;else re++;
    32         }
    33         for(rg int i=st[bl[y]];i<=y;i++){
    34             num = c[bl[y]-1][a[i]] - c[bl[x]][a[i]]  + (++tmp[a[i]]); 
    35             if(num==1)continue;
    36             if(num&1)re--;else re++;
    37         } 
    38         for(rg int i=x;i<=ed[bl[x]];i++)tmp[a[i]]=0;
    39         for(rg int i=st[bl[y]];i<=y;i++)tmp[a[i]]=0;
    40     }
    41     return re;
    42 }
    43 int main(){
    44     freopen("bzoj2821.in","r",stdin);
    45     freopen("bzoj2821.out","w",stdout);
    46     n=rd(); m=rd(); q=rd();
    47     u=sqrt(n),len=(n-1)/u+1;
    48     for(rg int i=1;i<=n;i++)a[i]=rd(),bl[i]=(i-1)/u+1;
    49     for(rg int i=1;i<=len;i++){
    50         st[i]=(i-1)*u+1,ed[i]=min(i*u,n);
    51         for(rg int j=st[i];j<=ed[i];j++)tmp[a[j]]++;
    52         for(rg int j=1;j<=m;j++)c[i][j]=tmp[j];
    53     }
    54     for(rg int i=1;i<=len;i++){
    55         int now=0;
    56         for(rg int j=1;j<=m;j++)tmp[j]=0;
    57         for(rg int j=i;j<=len;j++){
    58             for(rg int k=st[j];k<=ed[j];k++){
    59                 if((++tmp[a[k]])==1)continue;
    60                 if(tmp[a[k]]&1)now--;else now++;
    61             } 
    62             d[i][j]=now;
    63         }
    64     }
    65     for(rg int i=1;i<=m;i++)tmp[i]=0;
    66     int ans=0;
    67     for(rg int i=1;i<=q;i++){
    68         int l=(rd()+ans)%n+1,r=(rd()+ans)%n+1;
    69         if(l>r)swap(l,r);
    70         ans=query(l,r);
    71         printf("%d
    ",ans);
    72     }
    73     return 0;
    74 }
    bzoj2821

    bzoj2724

          区间众数,强制在线;      https://wenku.baidu.com/view/99bf0fc78662caaedd3383c4bb4cf7ec4afeb628.html

         不带修和上一个一样;预处理整块出现次数的前缀和,枚举散块

         带修的话修改一下分块大小暴力改,分块大小为$n^{frac{2}{3}}$,复杂度为$O( n^{ frac{5}{3} } )$ ;

     1 #include<bits/stdc++.h>
     2 #define il inline 
     3 #define rg register 
     4 using namespace std;
     5 const int N=40010,M=210;
     6 int n,m,c[M][N],d[M][M],tmp[N],sub[N],tot,a[N],bl[N];
     7 il char gc(){
     8     static char*p1,*p2,s[1000000];
     9     if(p1==p2)p2=(p1=s)+fread(s,1,1000000,stdin);
    10     return(p1==p2)?EOF:*p1++;
    11 }
    12 il int rd(){
    13     int x=0,f=1; char C=gc();
    14     while(C<'0'||C>'9'){C=gc();if(C=='-')f=-1;}
    15     while(C>='0'&&C<='9'){x=x*10+C-'0',C=gc();}
    16     return x*f;
    17 }
    18 int main(){
    19     freopen("bzoj2724.in","r",stdin);
    20     freopen("bzoj2724.out","w",stdout);
    21     n=rd(); m=rd();
    22     int u = sqrt(n) , len = (n-1)/u+1;
    23     for(rg int i=1;i<=n;i++)a[i]=sub[i]=rd(),bl[i]=(i-1)/u+1;
    24     sort(sub+1,sub+n+1);
    25     tot=unique(sub+1,sub+n+1)-sub-1;
    26     for(rg int i=1;i<=n;i++)a[i]=lower_bound(sub+1,sub+tot+1,a[i])-sub;
    27     for(rg int i=1;i<=len;i++){
    28         int li=u*(i-1)+1,ri=u*i;
    29         for(rg int j=li;j<=ri;j++)tmp[a[j]]++;
    30         for(rg int j=1;j<=tot;j++)c[i][j]=tmp[j];
    31     }
    32     for(rg int i=1;i<=len;i++){
    33         int mxv=0,mxd=0;
    34         for(rg int j=1;j<=tot;j++)tmp[j]=0; 
    35         for(rg int j=i;j<=len;j++){
    36             int lj=u*(j-1)+1,rj=u*j;    
    37             for(rg int k=lj;k<=rj;k++){
    38                 tmp[a[k]]++;
    39                 if(tmp[a[k]]>mxv||(tmp[a[k]]==mxv&&a[k]<mxd)){
    40                     mxd=a[k],mxv=tmp[a[k]];
    41                 }
    42             }
    43             d[i][j]=mxd;
    44         }
    45     }
    46     for(rg int j=1;j<=tot;j++)tmp[j]=0; 
    47     int ans=0,mx=0;
    48     for(rg int i=1;i<=m;i++){
    49         int l=(rd()+ans-1)%n+1,r=(rd()+ans-1)%n+1;
    50         if(l>r)swap(l,r); 
    51         if(bl[l]==bl[r]){
    52             ans=0;mx=0;
    53             for(rg int j=l;j<=r;j++){
    54                 tmp[a[j]]++;
    55                 if(tmp[a[j]]>mx||(tmp[a[j]]==mx&&a[j]<ans)){
    56                     ans=a[j],mx=tmp[a[j]];
    57                 }
    58             }
    59             for(rg int j=l;j<=r;j++)tmp[a[j]]=0;
    60         }else{
    61             int t=bl[l]*u;for(rg int j=l;j<=t;j++)tmp[a[j]]++;
    62             t=(bl[r]-1)*u+1;for(rg int j=t;j<=r;j++)tmp[a[j]]++;
    63             if(bl[l]<bl[r]-1)ans=d[bl[l]+1][bl[r]-1],mx=tmp[ans]+c[bl[r]-1][ans]-c[bl[l]][ans];
    64             else ans=0,mx=0;
    65             t=bl[l]*u;for(rg int j=l;j<=t;j++){
    66                 int now=tmp[a[j]]+c[bl[r]-1][a[j]]-c[bl[l]][a[j]];
    67                 if(now>mx||(now==mx&&a[j]<ans)){
    68                     mx=now;ans=a[j];
    69                 } 
    70                 tmp[a[j]]=0;
    71             }
    72             t=(bl[r]-1)*u+1;for(rg int j=t;j<=r;j++){
    73                 int now=tmp[a[j]]+c[bl[r]-1][a[j]]-c[bl[l]][a[j]]; 
    74                 if(now>mx||(now==mx&&a[j]<ans)){
    75                     mx=now;ans=a[j];
    76                 } 
    77                 tmp[a[j]]=0;
    78             }
    79         }
    80         ans=sub[ans];
    81         printf("%d",ans);
    82         puts("");
    83         //printf(" %d %d
    ",l,r);
    84     }
    85     return 0;
    86 }
    bzoj2724
  • 相关阅读:
    下拉列表实现模糊匹配选择
    Java读取修改Properties文件
    idea2018.2.4的安装激活与热部署插件JRebel的激活方法
    request.getScheme() 使用方法
    Navicat连接mysql8.0.1版本出现1251--Client does not support authentication protocol requested by server的解决
    javascript
    CSS第二节
    HTML+CSS
    mysql
    ubuntu常见错误
  • 原文地址:https://www.cnblogs.com/Paul-Guderian/p/10093651.html
Copyright © 2011-2022 走看看