POJ 2763 Housewife Wind 树链剖分 边权

来源:互联网 发布:c语言实现socket编程 编辑:程序博客网 时间:2024/05/18 20:31

单边更新,区间求和....套模板的题目,基本上没有什么难度,就是感觉点权和边权还是有一些差别的,不注意就错了...

#include<iostream>#include<cstdio>#include<cstring>#include<cstdlib>#include<algorithm>#include<iostream>#include<stack>using namespace std;#define MAXN 100100struct edge{    int u,v,next;} edge[MAXN*2];int head[MAXN],fa[MAXN],son[MAXN],num[MAXN];int dep[MAXN],p[MAXN],fp[MAXN],top[MAXN];int t,pos;void init(){    t=0;    memset(head,-1,sizeof(head));    pos=1;    memset(son,-1,sizeof(son));}void add(int u,int v){    edge[t].v=v;    edge[t].next=head[u];    head[u]=t++;}void dfs1(int u,int d){    dep[u]=d;    num[u]=1;    for(int i=head[u]; i!=-1; i=edge[i].next)    {        int v=edge[i].v;        if(v!=fa[u])        {            fa[v]=u;            dfs1(v,d+1);            num[u]+=num[v];            if(son[u]==-1||num[v]>num[son[u]])                son[u]=v;        }    }}void dfs2(int u,int sp){    top[u]=sp;    p[u]=pos++;    fp[p[u]]=u;    if(son[u]!=-1)        dfs2(son[u],sp);    for(int i=head[u]; i!=-1; i=edge[i].next)    {        int v=edge[i].v;        if(v!=son[u]&&v!=fa[u])            dfs2(v,v);    }}struct node{    int l,r,sum;} data[MAXN*4];void build(int l,int r,int k){    data[k].l=l;    data[k].r=r;    data[k].sum=0;    if(l==r)        return ;    int mid=(l+r)/2;    build(l,mid,k*2);    build(mid+1,r,k*2+1);}void updata(int x,int val,int k){    if(data[k].l==data[k].r&&data[k].l==x)    {        data[k].sum=val;        return ;    }    int mid=(data[k].l+data[k].r)/2;    if(x<=mid)        updata(x,val,k*2);    else        updata(x,val,k*2+1);    data[k].sum=data[k*2].sum+data[k*2+1].sum;}int query(int l,int r,int k){    if(data[k].l==l&&data[k].r==r)    {        return data[k].sum;    }    int mid=(data[k].l+data[k].r)/2;    if(r<=mid)        return query(l,r,k*2);    else if(l>mid)        return query(l,r,k*2+1);    else        return query(l,mid,k*2)+query(mid+1,r,k*2+1);}int finde(int u,int v){    int f1=top[u];    int f2=top[v];    int ans=0;    while(f1!=f2)    {        if(dep[f1]<dep[f2])        {            swap(f1,f2);            swap(u,v);        }        ans+=query(p[f1],p[u],1);        u=fa[f1];        f1=top[u];    }    if(u==v) return ans;    if(dep[u]>dep[v]) swap(u,v);    return ans+query(p[son[u]],p[v],1);}int e[MAXN][3];int main(){    int n,q,s;    while(scanf("%d %d %d",&n,&q,&s)!=EOF)    {        init();        for(int i=0;i<n-1; i++)        {            scanf("%d %d %d",&e[i][0],&e[i][1],&e[i][2]);            add(e[i][0],e[i][1]);            add(e[i][1],e[i][0]);        }        dfs1(1,0);        dfs2(1,1);        build(1,pos,1);        for(int i = 0; i < n-1; i++)        {            if(dep[e[i][0]] > dep[e[i][1]])                swap(e[i][0],e[i][1]);            updata(p[e[i][1]],e[i][2],1);        }        int f,x,y;        while(q--)        {            scanf("%d",&f);            if(f==0)            {                scanf("%d",&x);                printf("%d\n",finde(s,x));                s=x;            }            else            {                scanf("%d %d",&x,&y);                updata(p[e[x-1][1]],y,1);            }        }    }    return 0;}


0 0