标签:
You are given a tree (an acyclic undirected connected graph) with N nodes, and edges numbered 1, 2, 3...N-1.
We will ask you to perfrom some instructions of the following form:
The first line of input contains an integer t, the number of test cases (t <= 20). t test cases follow.
For each test case:
There is one blank line between successive tests.
For each "QUERY" operation, write one integer representing its result.
Input: 1 3 1 2 1 2 3 2 QUERY 1 2 CHANGE 1 3 QUERY 1 2 DONE Output: 1 3
题意:给一颗树,n个点,n-1条边,带边权,多次操作,操作有两种,改变某条边的边权,或者询问两个点的路径上的最大边权。
第一道树链剖分。
树链剖分就是把树拆成若干条链,首尾相接,然后用数据结构搞(线段树等).
#include<bits/stdc++.h> #define lson l,m,rt<<1 #define rson m+1,r,rt<<1|1 using namespace std; const int maxn=1000100; const int INF=(1<<29); int n; char op[20]; int u,v,w; vector<int> G[maxn]; int dep[maxn],son[maxn],fa[maxn],siz[maxn]; int top[maxn]; int id[maxn]; int num; int val[maxn]; struct Tree { int u,v,val; }; Tree e[maxn]; struct SegTree { int val; }; SegTree T[maxn<<2]; void dfs1(int u,int f,int d) { fa[u]=f; dep[u]=d; son[u]=0; siz[u]=1; for(int i=0;i<G[u].size();i++){ int v=G[u][i]; if(v==f) continue; dfs1(v,u,d+1); if(siz[v]>siz[son[u]]) son[u]=v; siz[u]+=siz[v]; } } void dfs2(int u,int tp) { top[u]=tp; id[u]=++num; if(son[u]) dfs2(son[u],tp); for(int i=0;i<G[u].size();i++){ int v=G[u][i]; if(v==fa[u]||v==son[u]) continue; dfs2(v,v); } } void push_up(int rt) { T[rt].val=max(T[rt<<1].val,T[rt<<1|1].val); } void build(int l,int r,int rt) { if(l==r){ T[rt].val=val[l]; return; } int m=(l+r)>>1; build(lson); build(rson); push_up(rt); } void update(int p,int c,int l,int r,int rt) { if(l==r){ T[rt].val=c; return; } int m=(l+r)>>1; if(p<=m) update(p,c,lson); else update(p,c,rson); push_up(rt); } int query(int L,int R,int l,int r,int rt) { if(L<=l&&r<=R) return T[rt].val; int m=(l+r)>>1; int res=-INF; if(L<=m) res=max(res,query(L,R,lson)); if(R>m) res=max(res,query(L,R,rson)); return res; } int cha(int u,int v) { int res=-INF; while(top[u]!=top[v]){ if(dep[top[u]]<dep[top[v]]) swap(u,v); res=max(res,query(id[top[u]],id[u],1,num,1)); u=fa[top[u]]; } if(u!=v){ if(dep[u]>dep[v]) swap(u,v); res=max(res,query(id[son[u]],id[v],1,num,1)); } return res; } int main() { //freopen("in.txt","r",stdin); int casen; cin>>casen; while(casen--){ cin>>n; for(int i=1;i<=n;i++) G[i].clear(); for(int i=1;i<n;i++){ scanf("%d%d%d",&u,&v,&w); e[i]={u,v,w}; G[u].push_back(v); G[v].push_back(u); } num=0; dfs1(1,0,1); dfs2(1,1); for(int i=1;i<n;i++){ if(dep[e[i].u]>dep[e[i].v]) swap(e[i].u,e[i].v); val[id[e[i].v]]=e[i].val; } build(1,num,1); while(~scanf("%s",op)){ if(op[0]==‘D‘) break; if(op[0]==‘C‘){ scanf("%d%d",&u,&w); int p=id[e[u].v]; update(p,w,1,num,1); } else{ scanf("%d%d",&u,&v); printf("%d\n",cha(u,v)); } } } return 0; }
标签:
原文地址:http://www.cnblogs.com/--560/p/4777344.html