• 【bzoj1086】 scoi2005—王室联邦


    http://www.lydsy.com/JudgeOnline/problem.php?id=1086 (题目链接)

    题意

      求将树分为几个联通块,每个联通块大小大于B小于3B,是否可行。

    Solution

      题都没看就翻了题解。。http://blog.csdn.net/popoqqq/article/details/42772237

    代码

    // bzoj3757
    #include<algorithm>
    #include<iostream>
    #include<cstring>
    #include<cstdlib>
    #include<cstdio>
    #include<cmath>
    #define MOD 1000000007
    #define inf 2147483640
    #define LL long long
    #define free(a) freopen(a".in","r",stdin);freopen(a".out","w",stdout);
    using namespace std;
    inline LL getint() {
        LL x=0,f=1;char ch=getchar();
        while (ch>'9' || ch<'0') {if (ch=='-') f=-1;ch=getchar();}
        while (ch>='0' && ch<='9') {x=x*10+ch-'0';ch=getchar();}
        return x*f;
    }
    
    const int maxn=1010;
    struct edge {int next,to;}e[maxn<<2];
    int head[maxn],size[maxn],pos[maxn],q[maxn],n,B,cnt,top,c,cap[maxn];
    
    
    void insert(int u,int v) {
        e[++cnt].to=v;e[cnt].next=head[u];head[u]=cnt;
        e[++cnt].to=u;e[cnt].next=head[v];head[v]=cnt;
    }
    void dfs(int x,int fa) {
        q[++top]=x;
        for (int i=head[x];i;i=e[i].next) if (e[i].to!=fa) {
                dfs(e[i].to,x);
                if (size[x]+size[e[i].to]>=B) {
                    size[x]=0;
                    cap[++cnt]=x;
                    while (q[top]!=x) pos[q[top--]]=cnt;
                }
                else size[x]+=size[e[i].to];
            }
        size[x]++;
    }
    void paint(int x,int fa,int c) {
        if (pos[x]) c=pos[x];
        else pos[x]=c;
        for (int i=head[x];i;i=e[i].next) if (e[i].to!=fa) paint(e[i].to,x,c);
    }
    int main() {
        scanf("%d%d",&n,&B);
        for (int i=1;i<n;i++) {
            int u,v;
            scanf("%d%d",&u,&v);
            insert(u,v);
        }
        if (n<B) {printf("0");return 0;}
        cnt=0;dfs(1,0);
        if (!cnt) cap[++cnt]=1;
        paint(1,0,cnt);
        printf("%d
    ",cnt);
        for (int i=1;i<=n;i++) printf("%d ",pos[i]);
        printf("
    ");
        for (int i=1;i<=cnt;i++) printf("%d ",cap[i]);
        return 0;
    }
    

      

  • 相关阅读:
    Java自学-多线程 常见线程方法
    Java自学-多线程 启动一个线程
    Java自学-Lambda 聚合操作
    Java自学-Lambda 方法引用
    Java自学-Lambda 概念
    Java自学-泛型 泛型转型
    Java自学-泛型 通配符
    Java自学-泛型 支持泛型的类
    <VCC笔记> 关于Assertion
    <VCC笔记>VCC简介与安装
  • 原文地址:https://www.cnblogs.com/MashiroSky/p/5914607.html
Copyright © 2020-2023  润新知