zoukankan      html  css  js  c++  java
  • [51nod][cf468D]1558 树中的配对

    http://www.51nod.com/onlineJudge/questionCode.html#!problemId=1558

    不是很懂dalao们用线段树是怎么写的……

    反正找出重心以后每个子树一个堆,再来个全局堆就吼了

    #include<queue>
    #include<stdio.h>
    #include<algorithm>
    #define MN 100001
    using namespace std;
    
    int read_p,read_ca;
    inline int read(){
        read_p=0;read_ca=getchar();
        while(read_ca<'0'||read_ca>'9') read_ca=getchar();
        while(read_ca>='0'&&read_ca<='9') read_p=read_p*10+read_ca-48,read_ca=getchar();
        return read_p;
    }
    struct na{int y,z,ne;}b[MN<<1];
    struct ma{int x,y;ma(int _x=0,int _y=0):x(_x),y(_y){}};
    bool operator < (ma a,ma b){return a.x<b.x;}
    priority_queue<ma> q[MN],Q,_q;
    int n,m,l[MN],x,y,z,ro,mi=1e9,si[MN],nm=0,num=0,be[MN];
    long long MMH;
    inline void in(int x,int y,int z){b[++num].y=y;b[num].z=z;b[num].ne=l[x];l[x]=num;}
    inline int min(int a,int b){return a<b?a:b;}
    int dfs(int x,int f){
        int S=1,s,u=0;
        for (register int i=l[x];i;i=b[i].ne)
        if (b[i].y!=f){
            s=dfs(b[i].y,x);
            if (u<s) u=s;
            S+=s;
            MMH+=1LL*b[i].z*min(s,n-s);
        }
        if (n-S>u) u=n-S;
        if (u<mi) ro=x,mi=u;
        return S;
    }
    void DFS(int x,int f,int d){
        q[d].push(ma{-x,d});si[d]++;be[x]=d;
        for (register int i=l[x];i;i=b[i].ne)
        if (b[i].y!=f) DFS(b[i].y,x,d);
    }
    int work(int u){
        while (_q.top().x!=q[_q.top().y].top().x||q[_q.top().y].empty()) _q.pop();
        ma o;
        if (_q.top().y==u) o=_q.top(),_q.pop();
        while (_q.top().x!=q[_q.top().y].top().x||q[_q.top().y].empty()) _q.pop();
        u=_q.top().y;
        if (o.x) _q.push(o);
        return u;
    }
    int main(){
        register int i;
        n=read();
        if (n==1) return puts("0
    1"),0;
        for (i=1;i<n;i++) x=read(),y=read(),z=read(),in(x,y,z),in(y,x,z);
        dfs(1,0);
        q[0].push(ma{-ro,0});_q.push(ma{-ro,0});si[0]=1;
        for (i=l[ro];i;i=b[i].ne)
        DFS(b[i].y,ro,++nm),Q.push(ma{si[nm]<<1,nm}),_q.push(ma(q[nm].top().x,nm));
        printf("%lld
    ",MMH<<1);
        for (i=1;i<=n;i++){
            while (Q.top().x!=si[Q.top().y]+q[Q.top().y].size()) Q.pop();
            if (be[i]==Q.top().y||Q.top().x<n-i+1) m=work(be[i]);else m=Q.top().y;
            if (i==ro&&-q[m].top().x>ro&&!q[0].empty()&&Q.top().x<n-i+1) m=0;
            printf("%d ",-q[m].top().x);
            q[m].pop();si[be[i]]--;if (!q[m].empty())_q.push(ma(q[m].top().x,m));
            Q.push(ma(si[m]+q[m].size(),m));Q.push(ma(si[be[i]]+q[be[i]].size(),be[i]));
        }
    }
    View Code
  • 相关阅读:
    校验文件数字签名的合法性(VerifyPE)
    windbg help
    VIM的常用操作
    使用Jsonp解决跨域数据访问问题
    Linux下不同文件编码的转换
    Segoe Font 介绍
    关于框架的一些思考
    Linux下Aptana Plugin For Eclipse的破解
    增强网站易用性的10个设计技巧
    Firebug中的console tab使用总结
  • 原文地址:https://www.cnblogs.com/Enceladus/p/6621654.html
Copyright © 2011-2022 走看看