zoukankan      html  css  js  c++  java
  • bzoj3731: Gty的超级妹子树(树分块)

    传送门

    分块树,代码参考了Manchery的

    具体细节还是看代码好了

    这题卡常……注意常数写好点……

      1 //minamoto
      2 #include<iostream>
      3 #include<cstdio>
      4 #include<algorithm>
      5 #include<cmath>
      6 #include<vector>
      7 using namespace std;
      8 #define getc() (p1==p2&&(p2=(p1=buf)+fread(buf,1,1<<21,stdin),p1==p2)?EOF:*p1++)
      9 char buf[1<<21],*p1=buf,*p2=buf;
     10 inline int read(){
     11     #define num ch-'0'
     12     char ch;bool flag=0;int res;
     13     while(!isdigit(ch=getc()))
     14     (ch=='-')&&(flag=true);
     15     for(res=num;isdigit(ch=getc());res=res*10+num);
     16     (flag)&&(res=-res);
     17     #undef num
     18     return res;
     19 }
     20 const int N=100005;
     21 struct Block{
     22     vector<int> a;
     23     inline void insert(int x){
     24         a.insert(lower_bound(a.begin(),a.end(),x+1),x);
     25     }
     26     inline void erase(int x){
     27         a.erase(lower_bound(a.begin(),a.end(),x));
     28     }
     29     inline void modify(int x,int y){
     30         erase(x),insert(y);
     31     }
     32     inline int query(int x){
     33         return a.end()-upper_bound(a.begin(),a.end(),x);
     34     }
     35     inline int size(){return a.size();}
     36 }Blo[N];
     37 int tot,ver[N<<2],head[N],Next[N<<2],first[N];
     38 inline void add(int u,int v){
     39     ver[++tot]=v,Next[tot]=head[u],head[u]=tot;
     40 }
     41 inline void addb(int u,int v){
     42     ver[++tot]=v,Next[tot]=first[u],first[u]=tot;
     43 }
     44 int n,B,a[N],fa[N],belong[N],bat[N],cnt;
     45 void dfs(int u,int f){
     46     fa[u]=f;
     47     if(u==1||Blo[belong[f]].size()==B)
     48     Blo[belong[u]=++cnt].insert(a[u]),addb(belong[f],belong[u]),bat[cnt]=belong[f];
     49     else Blo[belong[u]=belong[f]].insert(a[u]);
     50     for(int i=head[u];i;i=Next[i])
     51     if(ver[i]!=f) dfs(ver[i],u);
     52 }
     53 int Y,ans=0;
     54 void block_dfs(int u){
     55     ans+=Blo[u].query(Y);
     56     for(int i=first[u];i;i=Next[i])
     57     if(bat[ver[i]]==u) block_dfs(ver[i]);
     58 }
     59 void find(int u,int f){
     60     if(a[u]>Y) ++ans;
     61     for(int i=head[u];i;i=Next[i])
     62     if(ver[i]!=f&&fa[ver[i]]==u)
     63     if(belong[ver[i]]==belong[u]) find(ver[i],u);
     64     else block_dfs(belong[ver[i]]);
     65 }
     66 int c[N],d[N];
     67 void cont(int u,int f){
     68     c[++*c]=u;
     69     for(int i=head[u];i;i=Next[i])
     70     if(ver[i]!=f&&fa[ver[i]]==u)
     71     if(belong[ver[i]]==belong[u]) cont(ver[i],u);
     72     else d[++*d]=belong[ver[i]];
     73 }
     74 int main(){
     75     int q,op,u,v,lastans=0;
     76     //freopen("testdata.in","r",stdin);
     77     n=read(),B=sqrt(n);
     78     for(int i=1;i<n;++i)
     79     u=read(),v=read(),add(u,v),add(v,u);
     80     for(int i=1;i<=n;++i) a[i]=read();
     81     dfs(1,0);q=read();
     82     while(q--){
     83         op=read();
     84         switch(op){
     85             case 0:{
     86                 u=read(),v=read();
     87                 u^=lastans,v^=lastans;
     88                 Y=v,ans=0;
     89                 find(u,fa[u]);
     90                 printf("%d
    ",lastans=ans);
     91                 break;
     92             }
     93             case 1:{
     94                 u=read(),v=read();
     95                 u^=lastans,v^=lastans;
     96                 Blo[belong[u]].modify(a[u],v);
     97                 a[u]=v;
     98                 break;
     99             }
    100             case 2:{
    101                 u=read(),v=read();
    102                 u^=lastans,v^=lastans;
    103                 a[++n]=v;
    104                 add(u,n),add(n,u);
    105                 fa[n]=u;
    106                 if(Blo[belong[u]].size()==B)
    107                 Blo[belong[n]=++cnt].insert(a[n]),addb(belong[u],belong[n]),bat[cnt]=belong[u];
    108                 else Blo[belong[n]=belong[u]].insert(a[n]);
    109                 break;
    110             }
    111             case 3:{
    112                 u=read(),u^=lastans;
    113                 if(belong[u]!=belong[fa[u]]){
    114                     fa[u]=0,bat[belong[u]]=0;break;
    115                 }
    116                 cont(u,fa[u]);
    117                 belong[u]=++cnt;
    118                 for(int i=1;i<=*c;++i){
    119                     Blo[belong[fa[u]]].erase(a[c[i]]);
    120                     Blo[cnt].insert(a[c[i]]);
    121                     belong[c[i]]=cnt;
    122                 }
    123                 for(int i=1;i<=*d;++i)
    124                 addb(cnt,d[i]),bat[d[i]]=cnt;
    125                 fa[u]=0,*c=*d=0;
    126                 break;
    127             }
    128         }
    129     }
    130     return 0;
    131 }
  • 相关阅读:
    axios
    vue-cli-service 报错
    避免大型、复杂的布局和布局抖动
    vue 父子通信
    == 区别 === ,!= 区别 !==
    全选/取消全选
    vue 注意
    pyparsing:自定义一个属于你的语法解析器(更新中)
    《python解释器源码剖析》第11章--python虚拟机中的控制流
    collections:内建模块,提供额外的集合类
  • 原文地址:https://www.cnblogs.com/bztMinamoto/p/9588586.html
Copyright © 2011-2022 走看看