POJ 2763 Housewife Wind 树链剖分模板

来源:互联网 发布:苹果6移动数据怎么设置 编辑:程序博客网 时间:2024/06/06 02:23

时空隧道


题目大意:
一棵树,两种操作:①改变第x条边的权值②询问x到y的路径长度


分析:
树链剖分模板
(自认为代码写的还是比较好看滴….QAQ


代码如下:

#include<algorithm>#include<iostream>#include<cstring>#include<cstdio>//by NeighThornusing namespace std;const int maxn=100000+5;int n,S,q,hd[maxn],to[maxn*2],nxt[maxn*2],w[maxn*2],cnt,val[maxn],dep[maxn],fa[maxn],son[maxn],top[maxn],size[maxn]; struct edge{    int s,x,y;}e[maxn];struct Tree{    int l,r,sum;}tree[maxn*4];inline void add(int x,int y){    to[cnt]=y;    nxt[cnt]=hd[x];    hd[x]=cnt++;}inline void dfs1(int root,int f){    size[root]=1;    for(int i=hd[root];i!=-1;i=nxt[i])        if(to[i]!=f){            fa[to[i]]=root;            dep[to[i]]=dep[root]+1;dfs1(to[i],root);            size[root]+=size[to[i]];            if(son[root]==-1||size[to[i]]>size[son[root]])                son[root]=to[i];        }}inline void dfs2(int root,int f){    w[root]=++cnt,top[root]=f;    if(son[root]==-1)        return;    dfs2(son[root],f);    for(int i=hd[root];i!=-1;i=nxt[i])        if(to[i]!=fa[root]&&to[i]!=son[root])            dfs2(to[i],to[i]);}inline void build(int l,int r,int tr){    tree[tr].l=l,tree[tr].r=r;    if(l==r){        tree[tr].sum=val[l];        return;    }    int mid=(l+r)>>1;    build(l,mid,tr<<1),build(mid+1,r,tr<<1|1);    tree[tr].sum=tree[tr<<1].sum+tree[tr<<1|1].sum;}inline void change(int pos,int VAL,int tr){    if(tree[tr].l==tree[tr].r){        tree[tr].sum=VAL;        return;    }    int mid=(tree[tr].l+tree[tr].r)>>1;    if(pos<=mid)        change(pos,VAL,tr<<1);    else        change(pos,VAL,tr<<1|1);    tree[tr].sum=tree[tr<<1].sum+tree[tr<<1|1].sum;}inline int query(int l,int r,int tr){    if(tree[tr].l==l&&tree[tr].r==r)        return tree[tr].sum;    int mid=(tree[tr].l+tree[tr].r)>>1;    if(r<=mid)        return query(l,r,tr<<1);    else if(l>mid)        return query(l,r,tr<<1|1);    else        return query(l,mid,tr<<1)+query(mid+1,r,tr<<1|1);}inline void Change(int id,int VAL){    if(dep[e[id].x]>dep[e[id].y])        change(w[e[id].x],VAL,1);    else        change(w[e[id].y],VAL,1);}inline int Query(int u,int v){    int ans=0;    while(top[u]!=top[v]){        if(dep[top[u]]<dep[top[v]])            swap(u,v);        ans+=query(w[top[u]],w[u],1);        u=fa[top[u]];    }    if(dep[u]>dep[v])        swap(u,v);    if(u!=v)        ans+=query(w[son[u]],w[v],1);    return ans;}signed main(void){    cnt=0,memset(hd,-1,sizeof(hd));    memset(son,-1,sizeof(son));    scanf("%d%d%d",&n,&q,&S);    for(int i=1,x,y,s;i<n;i++)        scanf("%d%d%d",&e[i].x,&e[i].y,&e[i].s),add(e[i].x,e[i].y),add(e[i].y,e[i].x);    dep[1]=cnt=0;dfs1(1,-1);dfs2(1,1);    for(int i=1;i<n;i++){        if(dep[e[i].x]>dep[e[i].y])            val[w[e[i].x]]=e[i].s;        else            val[w[e[i].y]]=e[i].s;    }    build(1,n,1);    int x,y,cmd;    while(q--){        scanf("%d%d",&cmd,&x);        if(cmd==0)            cout<<Query(S,x)<<endl,S=x;        else            scanf("%d",&y),Change(x,y);    }    return 0;}

by >_< NeighThorn

1 0
原创粉丝点击