• 【Vijos】lxhgww的奇思妙想(长链剖分)


    题意:给定一棵n个点的树,m次强制在线的询问,每次询问x的k级祖先的编号

    n<=3e5,m<=1.8e6

    思路:参考资料:https://zhuanlan.zhihu.com/p/25984772

    https://blog.bill.moe/long-chain-subdivision-notes/

    不知道为什么写成f[v][0]=u会RE一部分,f[u][0]=fa就AC了,下次写长链剖分的时候注意

      1 #include<bits/stdc++.h>
      2 using namespace std;
      3 typedef long long ll;
      4 typedef unsigned int uint;
      5 typedef unsigned long long ull;
      6 typedef pair<int,int> PII;
      7 typedef pair<ll,ll> Pll;
      8 typedef vector<int> VI;
      9 typedef vector<PII> VII;
     10 typedef pair<ll,int>P;
     11 #define N  300010
     12 #define M  600010
     13 #define fi first
     14 #define se second
     15 #define MP make_pair
     16 #define pi acos(-1)
     17 #define mem(a,b) memset(a,b,sizeof(a))
     18 #define rep(i,a,b) for(int i=(int)a;i<=(int)b;i++)
     19 #define per(i,a,b) for(int i=(int)a;i>=(int)b;i--)
     20 #define lowbit(x) x&(-x)
     21 #define Rand (rand()*(1<<16)+rand())
     22 #define id(x) ((x)<=B?(x):m-n/(x)+1)
     23 #define ls p<<1
     24 #define rs p<<1|1
     25 
     26 const ll MOD=1e9+7,inv2=(MOD+1)/2;
     27       double eps=1e-6;
     28       ll INF=1ll<<62;
     29       ll inf=5e13;
     30       int dx[4]={-1,1,0,0};
     31       int dy[4]={0,0,-1,1};
     32 
     33 int f[N][20];
     34 vector<int> up[N],down[N];
     35 int head[M],vet[M],nxt[M],tot;
     36 int dep[M],son[M],top[M],len[M],hb[M],mx[M];
     37 
     38 int read()
     39 {
     40    int v=0,f=1;
     41    char c=getchar();
     42    while(c<48||57<c) {if(c=='-') f=-1; c=getchar();}
     43    while(48<=c&&c<=57) v=(v<<3)+v+v+c-48,c=getchar();
     44    return v*f;
     45 }
     46 
     47 void add(int a,int b)
     48 {
     49     nxt[++tot]=head[a];
     50     vet[tot]=b;
     51     head[a]=tot;
     52 }
     53 
     54 void dfs1(int u,int fa,int depth)
     55 {
     56     mx[u]=dep[u]=depth;
     57     f[u][0]=fa;
     58     rep(i,1,19) f[u][i]=f[f[u][i-1]][i-1];
     59     int e=head[u];
     60     while(e)
     61     {
     62         int v=vet[e];
     63         if(v!=fa)
     64         {
     65             dfs1(v,u,depth+1);
     66             if(mx[v]>mx[son[u]])
     67             {
     68                 son[u]=v;
     69                 mx[u]=mx[v];
     70             }
     71         }
     72         e=nxt[e];
     73     }
     74 }
     75 
     76 void dfs2(int u,int ance,int l)
     77 {
     78     len[u]=l;
     79     top[u]=ance;
     80     if(son[u])
     81     {
     82         dfs2(son[u],ance,l+1);
     83         len[u]=len[son[u]];
     84     }
     85     int e=head[u];
     86     while(e)
     87     {
     88         int v=vet[e];
     89         if(v!=f[u][0]&&v!=son[u]) dfs2(v,v,1);
     90         e=nxt[e];
     91     }
     92 }
     93 
     94 int query(int u,int k)
     95 {
     96     if(k>dep[u]) return 0;
     97     if(!k) return u;
     98     u=f[u][hb[k]];
     99     k-=(1<<hb[k]);
    100     if(!k) return u;
    101     if(dep[u]-dep[top[u]]==k) return top[u];
    102     if(dep[u]-dep[top[u]]>k) return down[top[u]][dep[u]-dep[top[u]]-k-1];
    103     return up[top[u]][k-(dep[u]-dep[top[u]])-1];
    104 }
    105 
    106 int main()
    107 {
    108     int n=read();
    109     rep(i,1,n) head[i]=0;
    110     tot=0;
    111     rep(i,1,n-1)
    112     {
    113         int x=read(),y=read();
    114         add(x,y);
    115         add(y,x);
    116     }
    117     dep[1]=0;
    118     dfs1(1,0,1);
    119     dfs2(1,1,1);
    120     rep(i,1,19)
    121      rep(j,(1<<(i-1)),((1<<i)-1)) hb[j]=i-1; //highbit
    122     rep(i,1,n)
    123      if(top[i]==i)
    124      {
    125          int k=i;
    126          rep(j,1,len[i])
    127          {
    128              k=f[k][0];
    129              up[i].push_back(k);
    130          }
    131          k=i;
    132          rep(j,1,len[i])
    133          {
    134              k=son[k];
    135              down[i].push_back(k);
    136          }
    137      }
    138 
    139     int m=read(),ans=0;
    140     rep(i,1,m)
    141     {
    142         int x=read(),k=read();
    143         x^=ans; k^=ans;
    144         ans=query(x,k);
    145         printf("%d
    ",ans);
    146     }
    147     return 0;
    148 }
  • 相关阅读:
    几道cf水题
    cf水题
    一道cf水题
    c++list用法
    c++map用法
    c++ vector常见用法
    c++string,常见用法总结
    复变函数考试后的反思
    [FZYZOJ 1204] 零和问题
    [FZYZOJ 1202] 金坷垃
  • 原文地址:https://www.cnblogs.com/myx12345/p/11545141.html
Copyright © 2020-2023  润新知