ACM Contest and Blackout UVA - 10600

 

In order to prepare the “The First National ACM School Contest”(in 20??) the major of the city decided to provide all the schools with a reliable source of power. (The major is really afraid of blackoutsJ). So, in order to do that, power station “Future” and one school (doesn’t matter which one) must be connected; in addition, some schools must be connected as well.

 

You may assume that a school has a reliable source of power if it’s connected directly to “Future”, or to any other school that has a reliable source of power. You are given the cost of connection between some schools. The major has decided to pick out two the cheapest connection plans – the cost of the connection is equal to the sum of the connections between the schools. Your task is to help the major – find the cost of the two cheapest connection plans.

 

Input

The Input starts with the number of test cases, T (1£T£15) on a line. Then T test cases follow. The first line of every test case contains two numbers, which are separated by a space, N (3£N£100) the number of schools in the city, and M the number of possible connections among them. Next M lines contain three numbers Ai, Bi, Ci , where Ci  is the cost of the connection (1£Ci£300) between schools Ai  and Bi. The schools are numbered with integers in the range 1 to N.

 

Output

For every test case print only one line of output. This line should contain two numbers separated by a single space - the cost of two the cheapest connection plans. Let S1 be the cheapest cost and S2 the next cheapest cost. It’s important, that S1=S2 if and only if there are two cheapest plans, otherwise S1£S2. You can assume that it is always possible to find the costs S1 and S2..

Sample Input

2

5 8

1 3 75

3 4 51

2 4 19

3 2 95

2 5 42

5 4 31

1 2 9

3 5 66

9 14

1 2 4

1 8 8

2 8 11

3 2 8

8 9 7

8 7 1

7 9 6

9 3 2

3 4 7

3 6 4

7 6 2

4 6 14

4 5 9

5 6 10


Sample Output

110 121

37 37

次小生成樹

#include<stdio.h>
#include<string.h>
#include<iostream>
#include<algorithm>
using namespace std;
struct STR
{
    int x,y,z;
}a[10001];
int tree[10001],mark[10001];
int find(int m)
{
    if(m==tree[m])
    return m;
    else
    return tree[m]=find(tree[m]);
}
void merge(int x,int y)
{
    int fx=find(x);
    int fy=find(y);
    if(fx>fy)
    tree[fx]=fy;
    else
    tree[fy]=fx;
}
bool comp(STR p,STR q)
{
    return p.z<q.z;
}
int main()
{
    int t,n,m,i,j,k,sum,sum1;
    scanf("%d",&t);
    while(t--)
    {
        memset(a,0,sizeof(a));
        scanf("%d%d",&m,&n);
       for(i=0;i<n;i++)
        {
            scanf("%d %d %d",&a[i].x,&a[i].y,&a[i].z);
        }
       sum=0;sort(a,a+n,comp);
        memset(mark,0,sizeof(mark));
        memset(tree,0,sizeof(tree));
        for(i=0;i<m;i++){tree[i]=i;}
        k=0;
        for(i=0;i<n;i++)
        {
            if(find(a[i].x)!=find(a[i].y))
            {
                merge(a[i].x,a[i].y);
                mark[i]=1;
                sum=sum+a[i].z;
                k++;
            }
            if(k>=m-1){break;}
        }
        int min=20000000;
        for(i=0;i<n;i++)
        {
            if(mark[i]==0)
            {
                memset(tree,0,sizeof(tree));
                for(j=0;j<m;j++){tree[j]=j;}
                merge(a[i].x,a[i].y);
                sum1=a[i].z;
                k=1;

                for(j=0;j<n;j++)
                {
                    if(find(a[j].x)!=find(a[j].y))
                    {
                        merge(a[j].x,a[j].y);
                        sum1=sum1+a[j].z;
                        k++;
                    }
                }
                if(sum1<min&&k==m-1)
                {
                    min=sum1;
                }
            }
        }
        printf("%d %d\n",sum,min);
    }
return 0;
}


發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章