欢迎访问生活随笔!

生活随笔

您现在的位置是:首页 > 形式科学 > 计算机科学 > IT网络

IT网络

[SCOI2015]信息传输

发布时间:2022-11-15IT网络 小博士
[SCOI2015]信息传输
BZOJ
洛古
考虑什么样的点将对查询做出回答,
设每一点的情报收集开始时间为(t_i),那么每一次询问都是问链中有多少点I满足$$now-t_i>c$$
术语的互换

[SCOI2015]情报传递

BZOJ
luogu
考虑什么样的点会对某个询问贡献答案,
设每个点的开始搜集情报时间为(t_i),那么每次询问就是要求链上有多少点i满足$$now-t_i>c$$
移项就有$$t_i<now-c$$
相当于求链上满足条件的点数,但是带修改依然不太好做
我们发现对于一个询问后面的修改操作的(t_i)一定大于now,所以后面修改的点一定不影响前面询问的答案,
想到什么?
可以离线询问,将所有修改操作处理完,最后直接主席树查就行了,复杂度(O(nlogn))

#include<bits/stdc++.h> using namespace std; const int _=2e5+5; int re(){ int x=0,w=1;char ch=getchar(); while(ch<'0'||ch>'9'){if(ch=='-')w=-1;ch=getchar();} while(ch>='0'&&ch<='9')x=x*10+ch-'0',ch=getchar(); return x*w; } bool vis[_]; vector<int>p[_]; int n,o,q,cnt,tot; int s[_*20],ls[_*20],rs[_*20]; int h[_],rt[_],t[_],a[_],b[_],lim[_],fa[_],f[_],lca[_],dep[_]; struct edge{int to,next;}e[_<<1]; void link(int u,int v){ e[++cnt]=(edge){v,h[u]};h[u]=cnt; e[++cnt]=(edge){u,h[v]};h[v]=cnt; } int find(int x){return x==f[x]?x:f[x]=find(f[x]);} void upd(int&x,int l,int r,int k){ s[++tot]=s[x]+1;ls[tot]=ls[x];rs[tot]=rs[x]; x=tot;if(l==r)return;int mid=l+r>>1; k<=mid?upd(ls[x],l,mid,k):upd(rs[x],mid+1,r,k); } int query(int A,int B,int C,int D,int l,int r,int k){ if(r<=k)return s[A]+s[B]-s[C]-s[D]; int mid=l+r>>1,res=query(ls[A],ls[B],ls[C],ls[D],l,mid,k); if(k>mid)res+=query(rs[A],rs[B],rs[C],rs[D],mid+1,r,k);return res; } void dfs(int u){ rt[u]=rt[fa[u]]; if(t[u])upd(rt[u],1,q,t[u]); for(int i=h[u];i;i=e[i].next){ int v=e[i].to;if(v==fa[u])continue; dep[v]=dep[u]+1;dfs(v);f[v]=u; } vis[u]=1; for(int i=0,j=p[u].size();i<j;i++){ int k=p[u][i],v=a[k]==u?b[k]:a[k]; if(vis[v])lca[k]=find(v); } } int main(){ n=re(); for(int i=1;i<=n;i++){ fa[i]=re();if(!fa[i])o=i; link(i,fa[i]);f[i]=i; } q=re();int op,x; for(int i=1;i<=q;i++){ op=re();x=re(); if(op==2&&!t[x])t[x]=i; if(op==1){ a[i]=x,b[i]=re(),lim[i]=i-re()-1; p[x].push_back(i);p[b[i]].push_back(i); } } dep[1]=1;dfs(o); for(int i=1;i<=q;i++) if(a[i])printf('%d %d ',dep[a[i]]+dep[b[i]]-dep[lca[i]]-dep[fa[lca[i]]],lim[i]>=1?query(rt[a[i]],rt[b[i]],rt[lca[i]],rt[fa[lca[i]]],1,q,lim[i]):0); return 0; }