zoukankan      html  css  js  c++  java
  • 莫队算法入门

    普通莫队「BZOJ2038」小Z的袜子

     1 #include<bits/stdc++.h>
     2 #define ll long long
     3 using namespace std;
     4 const int N=50010;
     5 int n,m,c[N],bel[N],siz,cnt[N];
     6 ll ans1[N],ans2[N];
     7 ll gcd(ll x,ll y){return y?gcd(y,x%y):x;}
     8 struct Node{
     9     int l,r,id;
    10     bool operator<(const Node& k)const{return bel[l]==bel[k.l]?r<k.r:l<k.l;}
    11 }que[N];
    12 int main(){
    13     scanf("%d%d",&n,&m);
    14     siz=sqrt(n);
    15     for(int i=1;i<=n;i++) scanf("%d",&c[i]),bel[i]=i/siz+1;
    16     for(int i=1;i<=m;i++) scanf("%d%d",&que[i].l,&que[i].r),que[i].id=i;
    17     sort(que+1,que+m+1);
    18     int ql=1,qr=0;
    19     ll sum1=0,sum2=0,len=0;
    20     for(int i=1;i<=m;i++){
    21         while(qr<que[i].r){
    22             qr++;
    23             sum1+=2*cnt[c[qr]],cnt[c[qr]]++;
    24             sum2+=2*len,len++;
    25         }
    26         while(ql>que[i].l){
    27             ql--;
    28             sum1+=2*cnt[c[ql]],cnt[c[ql]]++;
    29             sum2+=2*len,len++;
    30         }
    31         while(qr>que[i].r){
    32             sum1-=2*cnt[c[qr]]-2,cnt[c[qr]]--;
    33             sum2-=2*len-2,len--;
    34             qr--;
    35         }
    36         while(ql<que[i].l){
    37             sum1-=2*cnt[c[ql]]-2,cnt[c[ql]]--;
    38             sum2-=2*len-2,len--;
    39             ql++;
    40         }
    41         if(que[i].l==que[i].r||!sum1)
    42             ans1[que[i].id]=0,ans2[que[i].id]=1;
    43         else{
    44             ll g=gcd(sum1,sum2);
    45             ans1[que[i].id]=sum1/g,ans2[que[i].id]=sum2/g;
    46         }
    47     }
    48     for(int i=1;i<=m;i++) printf("%lld/%lld
    ",ans1[i],ans2[i]);
    49     return 0;
    50 }

    带修改莫队「BZOJ2120」数颜色

     1 #include<bits/stdc++.h>
     2 using namespace std;
     3 const int N=10010,C=1000010;
     4 int n,m,siz,bel[N],color[N],temp[N],pos[N],from[N],to[N],cnt[C],totc,totq,ans[N];
     5 struct Q{
     6     int l,r,t,id;//查询[l,r]在t次修改后的信息 
     7     bool operator<(const Q& k)const{
     8         if(bel[l]==bel[k.l]&&bel[r]==bel[k.r]) return t<k.t;
     9         if(bel[l]==bel[k.l]) return r<k.r;
    10         return l<k.l;
    11     }
    12 }que[N];
    13 int main(){
    14     char opt[10];
    15     int t1,t2;
    16     scanf("%d%d",&n,&m);
    17     siz=pow(n,2.0/3);
    18     for(int i=1;i<=n;i++) scanf("%d",&color[i]),temp[i]=color[i],bel[i]=i/siz+1;
    19     for(int i=1;i<=m;i++){
    20         scanf("%s%d%d",opt,&t1,&t2);
    21         if(opt[0]=='Q') que[++totq]=(Q){t1,t2,totc,totq};
    22         else totc++,pos[totc]=t1,to[totc]=t2,from[totc]=temp[t1],temp[t1]=t2;
    23     }
    24     sort(que+1,que+totq+1);
    25     int pl=1,pr=0,pt=0,res=0;
    26     for(int i=1;i<=totq;i++){
    27         while(pl>que[i].l){
    28             pl--;
    29             cnt[color[pl]]++;
    30             if(cnt[color[pl]==1]) res++;
    31         }
    32         while(pr<que[i].r){
    33             pr++;
    34             cnt[color[pr]]++;
    35             if(cnt[color[pr]]==1) res++;
    36         }
    37         while(pt<que[i].t){
    38             pt++;
    39             if(pos[pt]<=pr&&pos[pt]>=pl){
    40                 cnt[color[pos[pt]]]--;
    41                 if(!cnt[color[pos[pt]]]) res--;
    42             } 
    43             color[pos[pt]]=to[pt];
    44             if(pos[pt]<=pr&&pos[pt]>=pl){
    45                 cnt[color[pos[pt]]]++;
    46                 if(cnt[color[pos[pt]]]==1) res++;
    47             }
    48         }
    49         while(pt>que[i].t){
    50             if(pos[pt]<=pr&&pos[pt]>=pl){
    51                 cnt[color[pos[pt]]]--;
    52                 if(!cnt[color[pos[pt]]]) res--;
    53             }
    54             color[pos[pt]]=from[pt];
    55             if(pos[pt]<=pr&&pos[pt]>=pl){
    56                 cnt[color[pos[pt]]]++;
    57                 if(cnt[color[pos[pt]]]==1) res++;
    58             }
    59             pt--;
    60         }
    61         while(pl<que[i].l){
    62             cnt[color[pl]]--;
    63             if(!cnt[color[pl]]) res--;
    64             pl++;
    65         }
    66         while(pr>que[i].r){
    67             cnt[color[pr]]--;
    68             if(!cnt[color[pr]]) res--;
    69             pr--;
    70         }
    71         ans[que[i].id]=res;
    72     }
    73     for(int i=1;i<=totq;i++) printf("%d
    ",ans[i]);
    74     return 0;
    75 }

    树上莫队「UOJ58」[WC2013]糖果公园

      1 #include<bits/stdc++.h>
      2 #define ll long long
      3 #define R register
      4 using namespace std;
      5 const int N=100010,P=20,maxp=17;
      6 inline int read(){
      7     int x=0;char c=0;
      8     while(c<'0'||c>'9') c=getchar();
      9     while(c>='0'&&c<='9')x=(x<<3)+(x<<1)+c-'0',c=getchar();
     10     return x;
     11 }
     12 int n,m,q,c[N],temp[N],id[N<<1],totid,siz,bel[N],in[N],out[N],cnt[N];
     13 short vis[N]; //vis[i]λiÔÚÅ·À­ÐòÖгöÏֵĴÎÊý 
     14 ll v[N],w[N],ans[N];
     15 vector<int>g[N];
     16 int f[N][P],dep[N];
     17 struct Que{
     18     int l,r,t,id;//²éѯŷÀ­ÐòÖÐÇø¼ä[l,r]µÚt´ÎÐ޸ĺóµÄÐÅÏ¢ 
     19     bool operator<(const Que& k)const{
     20         if(bel[l]==bel[k.l]&&bel[r]==bel[k.r]) return t<k.t;
     21         return bel[l]==bel[k.l]?r<k.r:l<k.l;
     22     }
     23 }que[N];
     24 int totq,totc,from[N],to[N],pos[N];//pos½ÚµãµÄÑÕÉ«´ÓfromÐÞ¸ÄΪto 
     25 void dfs(int k,int fa,int d){
     26     int x;
     27     f[k][0]=fa,id[++totid]=k,dep[k]=d,in[k]=totid;
     28     for(R int i=0;i<g[k].size();i++){
     29         x=g[k][i];
     30         if(x==fa) continue;
     31         dfs(x,k,d+1);
     32     }
     33     id[++totid]=k,out[k]=totid;
     34     return;
     35 }
     36 inline int getlca(int x,int y){
     37     if(dep[x]<dep[y]) swap(x,y);
     38     for(int i=maxp;i>=0;i--)
     39         if(dep[f[x][i]]>=dep[y]) x=f[x][i];
     40     if(x==y) return x;
     41     for(int i=maxp;i>=0;i--)
     42         if(f[x][i]!=f[y][i]) x=f[x][i],y=f[y][i];
     43     return f[x][0];
     44 }
     45 int main(){
     46     int opt,t1,t2;
     47     n=read(),m=read(),q=read(),siz=pow(n,2.0/3);
     48     for(R int i=1;i<=m;i++) v[i]=read();
     49     for(R int i=1;i<=n;i++) w[i]=read(),bel[i]=i/siz+1;
     50     for(R int i=1;i<n;i++){t1=read(),t2=read();g[t1].push_back(t2);g[t2].push_back(t1);}
     51     for(R int i=1;i<=n;i++) c[i]=read(),temp[i]=c[i];
     52     dfs(1,0,1);
     53     for(R int j=1;j<=maxp;j++)
     54         for(R int i=1;i<=n;i++) f[i][j]=f[f[i][j-1]][j-1];
     55     for(R int i=1;i<=q;i++){
     56         opt=read(),t1=read(),t2=read();
     57         if(!opt) ++totc,from[totc]=temp[t1],to[totc]=t2,pos[totc]=t1,temp[t1]=t2;
     58         else{
     59             if(in[t1]>=in[t2]&&out[t1]<=out[t2]||in[t2]>=in[t1]&&out[t2]<=out[t1]) que[++totq]=(Que){min(in[t1],in[t2]),max(in[t1],in[t2]),totc,totq};
     60             else if(abs(in[t1]-out[t2])<abs(out[t1]-in[t2])) que[++totq]=(Que){min(in[t1],out[t2]),max(in[t1],out[t2]),totc,totq};
     61             else que[++totq]=(Que){min(in[t2],out[t1]),max(in[t2],out[t1]),totc,totq};
     62         }
     63     }
     64     sort(que+1,que+totq+1);
     65     int lca;
     66     R int x,pl=1,pr=0,pt=0;
     67     R ll res=0;
     68     for(R int i=1;i<=totq;i++){
     69         while(pl>que[i].l){
     70             x=id[--pl];
     71             if(!vis[x]) vis[x]=1,cnt[c[x]]++,res+=v[c[x]]*w[cnt[c[x]]];
     72             else if(vis[x]==1) res-=v[c[x]]*w[cnt[c[x]]],vis[x]=2,cnt[c[x]]--;
     73         }
     74         while(pr<que[i].r){
     75             x=id[++pr];
     76             if(!vis[x]) vis[x]=1,cnt[c[x]]++,res+=v[c[x]]*w[cnt[c[x]]];
     77             else if(vis[x]==1) res-=v[c[x]]*w[cnt[c[x]]],vis[x]=2,cnt[c[x]]--;
     78         }
     79         while(pt<que[i].t){
     80             pt++;
     81             x=pos[pt];
     82             if(vis[x]==1) res-=v[c[x]]*w[cnt[c[x]]],cnt[c[x]]--;
     83             c[x]=to[pt];
     84             if(vis[x]==1) cnt[c[x]]++,res+=v[c[x]]*w[cnt[c[x]]];
     85         }
     86         while(pt>que[i].t){
     87             x=pos[pt];
     88             if(vis[x]==1) res-=v[c[x]]*w[cnt[c[x]]],cnt[c[x]]--;
     89             c[x]=from[pt];
     90             if(vis[x]==1) cnt[c[x]]++,res+=v[c[x]]*w[cnt[c[x]]];
     91             pt--;
     92         }
     93         while(pl<que[i].l){
     94             x=id[pl];
     95             if(vis[x]==2) vis[x]=1,cnt[c[x]]++,res+=v[c[x]]*w[cnt[c[x]]];
     96             else if(vis[x]==1) res-=v[c[x]]*w[cnt[c[x]]],vis[x]=0,cnt[c[x]]--;
     97             pl++;
     98         }
     99         while(pr>que[i].r){
    100             x=id[pr];
    101             if(vis[x]==2) vis[x]=1,cnt[c[x]]++,res+=v[c[x]]*w[cnt[c[x]]];
    102             else if(vis[x]==1) res-=v[c[x]]*w[cnt[c[x]]],vis[x]=0,cnt[c[x]]--;
    103             pr--;
    104         }
    105         lca=getlca(id[que[i].l],id[que[i].r]);
    106         if(lca==id[que[i].l]||lca==id[que[i].r]) ans[que[i].id]=res;
    107         else ans[que[i].id]=res+v[c[lca]]*w[cnt[c[lca]]+1];
    108     }
    109     for(R int i=1;i<=totq;i++) printf("%lld
    ",ans[i]);
    110     return 0;
    111 }
  • 相关阅读:
    调用webservice接口报错
    Java设计模式之使用反序列化的方式实现单例模式
    Java设计模式之使用枚举类的方式创建单例
    使用饿汉模式创建单例模式
    Java 查看运行生成的字节码文件 反汇编
    Java设计模式之--单例模式-使用懒汉模式创建
    git无法 cherry pick到其他分支
    Android之Handler用法总结
    Java之观察者模式
    Android之Activity与Service通信
  • 原文地址:https://www.cnblogs.com/mycups/p/8529351.html
Copyright © 2011-2022 走看看