Connecting Universities

链接:http://acm.hust.edu.cn/vjudge/problem/427647/origin

题目:

Treeland is a country in which there are n towns connected by n - 1 two-way road such that it's possible to get from any town to any other town.

In Treeland there are 2k universities which are located in different towns.

Recently, the president signed the decree to connect universities by high-speed network.The Ministry of Education understood the decree in its own way and decided that it was enough to connect each university with another one by using a cable. Formally, the decree will be done!

To have the maximum sum in the budget, the Ministry decided to divide universities into pairs so that the total length of the required cable will be maximum. In other words, the total distance between universities in k pairs should be as large as possible.

Help the Ministry to find the maximum total distance. Of course, each university should be present in only one pair. Consider that all roads have the same length which is equal to 1.



题意:有一些城市和一些大学,每个城市有0-1个大学。有的城市间有公路,长度均为一,要求大学成对联通上网线,问网线最长是多少(重叠部分单独计算)

分析:用节点造图,记录大学个数,链接个数。完毕后遍历,找到度为一的点,删去,如果有大学结果加一,同时删去所连接的边,一层层删去,得到结果。

题解:
#include <iostream>
#include <cstdio>
#include <cstdlib>
#include <algorithm>
#include <queue>
#include <stack>
#include <vector>
#include <map>
#include <string>
#include <cstring>
#include <functional>
#include <cmath>
#include <cctype>
#include <cfloat>
#include <climits>
#include <complex>
#include <deque>
#include <list>
#include <set>
#include <utility>
using namespace std;


struct node{
	int uni;
	set<int> ar;
};
vector<node> vec;
struct cmp{
	bool operator()(int a,int b)
	{
		return (vec[a].ar.size()==vec[b].ar.size())?
			(vec[a].uni>vec[b].uni):(vec[a].ar.size()>vec[b].ar.size());
	}
};

int main()
{
	int n;
	int k;
	//freopen("in.txt","r",stdin);
	while(~scanf("%d %d",&n,&k))
	{
		vec.clear();
		vec.resize(n+1);
		for(int f=1;f<=n;f++)
			vec[f].uni=0;
		for(int i=1;i<=2*k;i++)
		{
			int ss;
			cin>>ss;
			vec[ss].uni++;
		}
		for(int j=1;j<n;j++)
		{
			int tx,ty;
			cin>>tx>>ty;
			vec[tx].ar.insert(ty);
			vec[ty].ar.insert(tx);
		}
		priority_queue<int,vector<int>,cmp> pq;
		for(int w=1;w<=n;w++)
			if(vec[w].ar.size()==1)
				pq.push(w);
		__int64 ans=0;	
		while(pq.size()>1)
		{
			int t=pq.top();
			pq.pop();
			ans+=vec[t].uni;
			vec[*vec[t].ar.begin()].uni+=vec[t].uni;
			vec[*vec[t].ar.begin()].ar.erase(t);
			if(vec[*vec[t].ar.begin()].ar.size()==1)
				pq.push(*vec[t].ar.begin());
		}
		//sort(no+1,no+n+1);
		printf("%I64d\n",ans);
	}
	return 0;
}

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值