Run ID | 作者 | 问题 | 语言 | 测评结果 | 分数 | 时间 | 内存 | 代码长度 | 提交时间 |
---|---|---|---|---|---|---|---|---|---|
51816 | LinkZelda | 树上博弈 | C++ | 通过 | 100 | 507 MS | 23548 KB | 3907 | 2022-07-13 15:03:36 |
#include<cstdio> #include<algorithm> #include<ctype.h> #include<cstring> #include<iostream> #include<vector> #include<queue> #include<ctime> #include<cmath> #include<queue> #include<map> #include<set> #include<unordered_map> #include<stack> #define pr pair<int,int> #define eps 1e-8 #define db double using namespace std; inline int read() { int x=0,f=1; char ch=getchar(); while(!isdigit(ch)) { if(ch=='-')f=-1; ch=getchar(); } while(isdigit(ch)) { x=x*10+ch-'0'; ch=getchar(); } return x*f; } const int N=200005; int w[N],head[N],to[N],nxt[N],cnt; void add(int u,int v,int wi) { to[++cnt]=v; nxt[cnt]=head[u]; head[u]=cnt; w[cnt]=wi; } int dfsn[N],tp[N],sz[N],son[N],fa[N],dep[N],tot; int a[N],n,q,st[N],ed[N]; void dfs1(int now,int fath) { fa[now]=fath; dfsn[++tot]=now; st[now]=tot; dep[now]=dep[fath]+1; sz[now]=1; for(int i=head[now]; i; i=nxt[i]) { int v=to[i]; if(v==fath) continue; dfs1(v,now); a[v]=w[i]; sz[now]+=sz[v]; if(sz[son[now]]<sz[v]) son[now]=v; } dfsn[++tot]=now; ed[now]=tot; } void dfs2(int now,int t) { tp[now]=t; if(!son[now]) return; dfs2(son[now],t); for(int i=head[now]; i; i=nxt[i]) { int v=to[i]; if(v==fa[now]||v==son[now]) continue; dfs2(v,v); } } int LCA(int x,int y) { while(tp[x]!=tp[y]) { if(dep[tp[x]]<dep[tp[y]]) swap(x,y); x=fa[tp[x]]; } return dep[x]>dep[y]?y:x; } int block; struct Node { int L,R,r,num,ty; Node(int L=0,int R=0,int r=0,int num=0,int ty=0):L(L),R(R),r(r),num(num),ty(ty) {} friend bool operator < (Node x,Node y) { if((x.L/block)!=(y.L/block)) return x.L/block<y.L/block; return ((x.L/block)&1)?x.R<y.R:x.R>y.R; } } que[N]; bool vis[N]; int anss,ans[N]; bool val[N]; int bb,s[1005],t[1005],sum[1005],bein[N]; void pre_work() { bb=sqrt(n); for(int i=1; i<=bb; i++) s[i]=(i-1)*bb+1,t[i]=i*bb; t[bb]=n; for(int i=1; i<=bb; i++) for(int j=s[i]; j<=t[i]; j++) bein[j]=i; } int cal(int r) { int ovo=bein[r],ret1=0,ret2=0; for(int i=1; i<ovo; i++) ret1+=sum[i]; for(int i=s[ovo]; i<=r; i++) ret1+=val[i]; if(!ret1) return r; for(int i=1; i<=ovo; i++) { if(ret2+sum[i]>=ret1) { for(int j=s[i]; j<=t[i]; j++) { ret2+=val[j]; if(ret2==ret1) return r-j; } } else ret2+=sum[i]; } } void work(int x) { if(a[x]) { if(val[a[x]]) sum[bein[a[x]]]--; else sum[bein[a[x]]]++; val[a[x]]^=1; } } int main() { // freopen("game3.in","r",stdin); // freopen("game3.out","w",stdout); n=read(); pre_work(); for(int u,v,wi,i=1; i<n; i++) u=read(),v=read(),wi=read(),add(u,v,wi),add(v,u,wi); dfs1(1,0); dfs2(1,1); q=read(); block=sqrt(q); for(int i=1; i<=q; i++) { int x=read(),y=read(),r=read(); int lca=LCA(x,y); if(lca==x) que[i]=Node(st[x],st[y],r,i,lca); else if(lca==y) que[i]=Node(st[y],st[x],r,i,lca); else { if(st[x]>st[y]) que[i]=Node(ed[x],st[y],r,i,0); else que[i]=Node(ed[y],st[x],r,i,0); } } sort(que+1,que+q+1); int nr=1,nl=2; for(int i=1; i<=q; i++) { while(nr<que[i].R) work(dfsn[++nr]); while(nl>que[i].L) work(dfsn[--nl]); while(nl<que[i].L) work(dfsn[nl++]); while(nr>que[i].R) work(dfsn[nr--]); if(que[i].ty) work(que[i].ty); // printf("AWA::%d\n",que[i].num); ans[que[i].num]=cal(que[i].r); if(que[i].ty) work(que[i].ty); } for(int i=1; i<=q; i++) printf("%d\n",ans[i]); // fclose(stdin); // fclose(stdout); return 0; }