• BZOJ 3011 Running Away From the Barn


    从下到上合并。

    可并堆,显然可以打标记。

    要开LONG LONG不然WA得很爽。

    #include<iostream>
    #include<cstdio>
    #include<cstring>
    #include<algorithm>
    #define maxv 200500
    #define maxe 200500
    using namespace std;
    struct edge
    {
        long long v,w,nxt;
    }e[maxe];
    long long nume=0,g[maxv],n,l,x,y,w;
    long long tree[maxv][3],size[maxv],val[maxv],lazy[maxv];
    long long ans[maxv],top[maxv],dis[maxv];
    void addedge(long long u,long long v,long long w)
    {
        e[++nume].v=v;
        e[nume].w=w;
        e[nume].nxt=g[u];
        g[u]=nume;
    }
    void pushdown(long long x)
    {
        if (lazy[x])
        {
            long long ls=tree[x][1],rs=tree[x][2];
            if (ls) {lazy[ls]+=lazy[x];val[ls]+=lazy[x];}
            if (rs) {lazy[rs]+=lazy[x];val[rs]+=lazy[x];}
            lazy[x]=0;    
        }
    }
    void pushup(long long x)
    {
        if (dis[tree[x][1]]<dis[tree[x][2]]) swap(tree[x][1],tree[x][2]);
        long long ls=tree[x][1],rs=tree[x][2];
        if (rs==0) dis[x]=0;
        else dis[x]=dis[rs]+1;
        size[x]=size[ls]+size[rs]+1;
    }
    long long merge(long long a,long long b)
    {
        if (a==0) return b;
        if (b==0) return a;
         if (val[a]<val[b]) swap(a,b);
        pushdown(a);
        tree[a][2]=merge(tree[a][2],b);
        pushup(a);
        return a;
    }
    long long pop(long long x)
    {
        long long ls=tree[x][1],rs=tree[x][2];
        tree[x][1]=0;tree[x][2]=0;
        return merge(ls,rs);
    }
    void dfs(long long x)
    {
        long long root=x;
        for (long long i=g[x];i;i=e[i].nxt)
        {
            long long v=e[i].v;
            dfs(v);
        }
        for (long long i=g[x];i;i=e[i].nxt)
        {
            long long v=e[i].v;
            lazy[top[v]]+=e[i].w;val[top[v]]+=e[i].w;
            root=merge(root,top[v]);
        }
        while (val[root]>l) root=pop(root);
        top[x]=root;ans[x]=size[root];
    }
    int main()
    {
        scanf("%lld%lld",&n,&l);
        for (long long i=1;i<=n;i++) size[i]=1;
        for (long long i=2;i<=n;i++)
        {
            scanf("%lld%lld",&x,&y);
            addedge(x,i,y);
        }
        dfs(1);
        for (long long i=1;i<=n;i++)    
            printf("%lld
    ",ans[i]);
        return 0;
    }
  • 相关阅读:
    2018百度之星初赛B轮 rect
    八数码问题(九宫格重排) 利用康托展开 判重
    2018百度之星初赛A轮 度度熊拼三角
    2018百度之星初赛A轮 度度熊学队列
    MongoDB(课时22 唯一索引)
    MongoDB(课时21 索引)
    MongoDB(课时20 游标)
    MongoDB(课时19 数据删除)
    MongoDB(课时18 修改器)
    MongoDB(课时17 更新函数)
  • 原文地址:https://www.cnblogs.com/ziliuziliu/p/5479414.html
Copyright © 2020-2023  润新知