1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102
|
#include <cstdlib> #include <algorithm> #include <cstring> #include <cctype> #define INF 2000000000 using namespace std; typedef long long ll; int (){ int f=1,x=0;char c=getchar(); while(c<'0'||c>'9'){if(c=='-')f=-f;c=getchar();} while(c>='0'&&c<='9')x=x*10+c-'0',c=getchar(); return f*x; } int n,m,fa[200005]={0},ch[200005][2],siz[200005]={0},rev[200005]={0}; int val[200005],to[200005]; int cmp(int k){ return ch[fa[k]][1]==k; } int isroot(int k){ return ch[fa[k]][0]!=k&&ch[fa[k]][1]!=k; } void Rev(int k){ swap(ch[k][0],ch[k][1]); rev[k]^=1; } void maintain(int k){ siz[k]=siz[ch[k][0]]+siz[ch[k][1]]+1; } void pushdown(int k){ if(k&&rev[k]){ rev[k]=0; if(ch[k][0])Rev(ch[k][0]); if(ch[k][1])Rev(ch[k][1]); } } void pushup(int k){ if(!k)return ; if(!isroot(k))pushup(fa[k]); pushdown(k); } void Rotate(int k){ int Fa=fa[k],Gfa=fa[Fa],d=cmp(k); ch[Fa][d]=ch[k][d^1],fa[ch[k][d^1]]=Fa; ch[k][d^1]=Fa,fa[Fa]=k; fa[k]=Gfa; if(!isroot(Fa)){ if(Fa==ch[Gfa][0])ch[Gfa][0]=k; else if(Fa==ch[Gfa][1])ch[Gfa][1]=k; } maintain(Fa); } void splay(int k){ pushup(k); for(int Fa=fa[k];!isroot(k);Rotate(k),Fa=fa[k]) if(fa[Fa]&&!isroot(Fa))Rotate(cmp(k)==cmp(Fa)?Fa:k); maintain(k); } void access(int k){ for(int t=0;k;t=k,k=fa[k])splay(k),ch[k][1]=t,maintain(k); } void makeroot(int k){ access(k),splay(k),Rev(k); } int findroot(int k){ while(fa[k])k=fa[k];return k; } void Split(int u,int v){ makeroot(u),access(v),splay(v); } void cut(int u,int v){ Split(u,v); ch[v][0]=fa[u]=0; maintain(v); } void link(int u,int v){ makeroot(u),fa[u]=v; } void init(){ n=read(),siz[n+1]=1; for(int i=1;i<=n;i++)val[i]=read(),to[i]=min(n+1,i+val[i]),siz[i]=1; for(int i=1;i<=n;i++)link(i,to[i]); } void solve(){ m=read(); int opr,x,y; while(m--){ opr=read(),x=read()+1; if(opr==1) Split(x,n+1),printf("%dn",siz[n+1]-1); if(opr==2){ y=read(); if(to[x]==n+1&&x+y>n)continue; cut(x,to[x]),val[x]=y,to[x]=min(x+y,n+1),link(x,to[x]); } } } int main(){ init(); solve(); return 0; }
|
近期评论