zoukankan      html  css  js  c++  java
  • 免费道路 BZOJ 3624

    免费道路

    【输入样例】

    5 7 2
    1 3 0
    4 5 1
    3 2 0
    5 3 1
    4 3 0
    1 2 1
    4 2 1

    【输出样例】

    3 2 0
    4 3 0
    5 3 1
    1 2 1


    题解:

    题意即为求一棵刚好拥有k条鹅卵石路的生成树

    那么我们先将所有水泥路加入图中

    就可以知道必须要加入的鹅卵石路

    这些边加入新树

    接下来再随意地按树的结构加入至k条鹅卵石路

    并再更加随意按树结构加水泥路至连通

    那么就得到了合法方案

    判断过程中无解的情况:

    1.所有边加入都无法连通

    2.鹅卵石路不足k条

    #include<algorithm>
    #include<iostream>
    #include<cstring>
    #include<cstdlib>
    #include<cstdio>
    #include<cmath>
    using namespace std;
    const int me = 1000233;
    struct shape
    {
        int x, y, z;
    };
    shape a[me], ans[me];
    int tot, num, cnt;
    int n, m, k;
    int fat[me];
    inline int Get()
    {
        int x = 0;
        char c = getchar();
        while('0' > c || c > '9') c = getchar();
        while('0' <= c && c <= '9')
        {
            x = (x << 3) + (x << 1) + c - '0';
            c = getchar();
        }
        return x;
    }
    int Find(int x)
    {
        return (fat[x] != x) ? fat[x] = Find(fat[x]) : x;
    }
    int main()
    {
        n = Get(), m = Get(), k = Get();
        for(int i = 1; i <= n; ++i) fat[i] = i;
        for(int i = 1; i <= m; ++i)
        {
            a[i].x = Get(), a[i].y = Get(), a[i].z = Get();
            if(a[i].z)
            {
                int u = Find(a[i].x);
                int v = Find(a[i].y);
                if(u != v) fat[u] = v, ++cnt;
            }
        }
        for(int i = 1; i <= m; ++i)
            if(!a[i].z)
            {
                int u = Find(a[i].x);
                int v = Find(a[i].y);
                if(u != v)
                {
                    fat[u] = v;
                    ans[++tot] = a[i];
                }
            }
        if(cnt + tot != n - 1)
        {
            printf("no solution
    ");
            return 0;
        }
        for(int i = 1; i <= n; ++i) fat[i] = i;
        for(int i = 1; i <= tot; ++i)
        {
            int u = Find(ans[i].x);
            int v = Find(ans[i].y);
            if(u != v) fat[u] = v;
        }
        num = tot;
        if(num != k)
            for(int i = 1; i <= m; ++i)
                if(!a[i].z)
                {
                    int u = Find(a[i].x);
                    int v = Find(a[i].y);
                    if(u != v)
                    {
                        ++num;
                        fat[u] = v;
                        ans[++tot] = a[i];
                        if(num == k) break;
                    }
                }
        if(num != k)
        {
            printf("no solution
    ");
            return 0;
        }
        for(int i = 1; i <= m; ++i)
            if(a[i].z)
            {
                int u = Find(a[i].x);
                int v = Find(a[i].y);
                if(u != v)
                {
                    fat[u] = v;
                    ans[++tot] = a[i];
                    if(tot == n - 1) break;
                }
            }for(int i = 1; i <= tot; ++i)
            printf("%d %d %d
    ", ans[i].x, ans[i].y, ans[i].z);
    }
  • 相关阅读:
    2018 Wannafly summer camp Day2--New Game!
    2018 Wannafly summer camp Day8--区间权值
    2018 Wannafly summer camp Day3--Shopping
    2018 Wannafly summer camp Day3--Travel
    HDU 6354--Everything Has Changed(判断两圆关系+弧长计算)
    Spring boot-(2) Spring Boot使用
    Spring boot-(1) Spring Boot快速开始
    Quartz使用(5)
    Quartz使用(4)
    Quartz使用(3)
  • 原文地址:https://www.cnblogs.com/lytccc/p/6221493.html
Copyright © 2011-2022 走看看