zoukankan      html  css  js  c++  java
  • BZOJ 1036: [ZJOI2008]树的统计Count(树链剖分)

    第一次打树链剖分,也挺容易的嘛~~~,两次dfs后建线段树维护就行了~~~

    CDOE:

    1
    #include<cstdio>
    #include<iostream>
    #include<cstring>
    #include<algorithm>
    using namespace std;
    #define maxn 30010
    struct edges{
        int to,next;
    }edge[maxn*2];
    int next[maxn],l;
    int addedge(int from,int to){
        edge[++l]=(edges){to,next[from]};
        next[from]=l;return 0;
    }
    int dep[maxn],par[maxn],si[maxn],ch[maxn];
    bool b[maxn];
    int dfs(int u){
        dep[u]=dep[par[u]]+1;
        b[u]=0;
        si[u]=1;
        for (int i=next[u];i;i=edge[i].next)
        if (b[edge[i].to]) { 
            par[edge[i].to]=u;
            dfs(edge[i].to);
            si[u]+=si[edge[i].to];
            if (si[ch[u]]<si[edge[i].to]) ch[u]=edge[i].to;
        }
        return 0;
    }
    int top[maxn],id[maxn],arr[maxn],pos[maxn];
    int ind,num;
    int heavy_edge(int x,bool flag){
        if (flag) top[++ind]=x;
        id[x]=ind;
        b[x]=0;
        arr[pos[x]=++num]=x;
        if (ch[x]) heavy_edge(ch[x],0);
        for (int i=next[x];i;i=edge[i].next)
        if (b[edge[i].to]){
            heavy_edge(edge[i].to,1);
        }
        return 0;
    }
    struct node{
        int l,r,Max,Sum;
    }t[maxn*4];
    int w[maxn];
    int buildtree(int x,int l,int r){
        t[x].l=l;t[x].r=r;
        if (l==r) {t[x].Max=t[x].Sum=w[arr[l]];return 0;}
        buildtree(x<<1,l,(l+r)>>1);
        buildtree((x<<1)+1,((l+r)>>1)+1,r);
        t[x].Max=max(t[x<<1].Max,t[(x<<1)+1].Max);
        t[x].Sum=t[x<<1].Sum+t[(x<<1)+1].Sum;
        return 0;
    }
    int n;
    int init(){
        scanf("%d",&n);
        for (int i=1;i<n;i++){
        int x,y;
        scanf("%d%d",&x,&y);
        addedge(x,y);addedge(y,x);
        }
        memset(b,true,sizeof(b));
        dfs(1);
        memset(b,true,sizeof(b));
        heavy_edge(1,1);
        for (int i=1;i<=n;i++) scanf("%d",w+i);
        buildtree(1,1,n);
        return 0;
    }
    int change(int x,int y){
        int l=t[x].l,r=t[x].r;
        if (y<l||y>r) return 0;
        if (l==r) {t[x].Max=t[x].Sum=w[arr[y]];return 0;}
        change(x<<1,y);change((x<<1)+1,y);
        t[x].Max=max(t[x<<1].Max,t[(x<<1)+1].Max);
        t[x].Sum=t[x<<1].Sum+t[(x<<1)+1].Sum;
        return 0;
    }
    int gmax(int x,int x1,int y1){
        int l=t[x].l,r=t[x].r;
        if (l>y1||r<x1) return -30002;
        if (l>=x1&&r<=y1) return (t[x].Max);
        return(max(gmax(x<<1,x1,y1),gmax((x<<1)+1,x1,y1)));
    }
    int gsum(int x,int x1,int y1){
        int l=t[x].l,r=t[x].r;
        if (l>y1||r<x1) return 0;
        if (l>=x1&&r<=y1) return (t[x].Sum);
        return(gsum(x<<1,x1,y1)+gsum((x<<1)+1,x1,y1));
    }
    int MAX(int l,int r){
        int ans=-30001;
        while (1){
        if (dep[top[id[l]]]<dep[top[id[r]]]) swap(l,r);
        if (id[l]!=id[r]) {ans=max(ans,gmax(1,pos[top[id[l]]],pos[l]));l=par[top[id[l]]];}
        else {if (dep[l]<dep[r]) swap(l,r);ans=max(ans,gmax(1,pos[r],pos[l]));return ans;}
        }
    }
    int SUM(int l,int r){
        int ans=0;
        while (1){
        if (dep[top[id[l]]]<dep[top[id[r]]]) swap(l,r);
        if (id[l]!=id[r]) {ans+=gsum(1,pos[top[id[l]]],pos[l]);l=par[top[id[l]]];}
        else {if (dep[l]<dep[r]) swap(l,r);ans+=gsum(1,pos[r],pos[l]);return ans;}
        }
    }
    int m;
    int work(){
        scanf("%d",&m);
        for (int i=1;i<=m;i++) {
        int x,y;char s[10];
        scanf("%s%d%d",s,&x,&y);
        if (s[0]=='C') {w[x]=y;change(1,pos[x]);}
        if (s[1]=='M') {printf("%d ",MAX(x,y));}
        if (s[1]=='S') {printf("%d ",SUM(x,y));}
        }
        return 0;
    }
    int main(){
        init();
        work();
        return 0;
    }
  • 相关阅读:
    CF-911E.Stack Sorting(栈)
    随机算法 && CodeForces
    CF-579D."Or" Game(或运算)
    CF-242E.XOR on Segment(异或线段树)
    莫队 && 洛谷 P1494 [国家集训队]小Z的袜子
    洛谷 P4168 [Violet]蒲公英(分块)
    分块 && 洛谷 P2801 教主的魔法
    启发式合并 && U41492 树上数颜色
    使用mysqlbinlog server远程备份binlog的脚本
    mysqldump备份过程中都干了些什么
  • 原文地址:https://www.cnblogs.com/New-Godess/p/4348960.html
Copyright © 2011-2022 走看看