(水)安慰奶牛 蓝桥杯

分析:最小生成树的一个变形。首先,最终必定是一颗树,先随便画一颗树然后自己模拟走一遍,会发现应该把连接某条边的2个顶点的权值加入到边权中,且边权应该乘2,所以最终以2l+point1+point2为边权生成最小生成树即可,至于起点在哪都不影响,只是因为睡前还要安慰一遍睡觉的顶点的奶牛(即起点的奶牛)所以选出最小的ci即可。

直接上代码:

#include<cstdio>                 //安慰奶牛 蓝桥  最小生成树
#include<algorithm>
using namespace std;
#define Max 100000+5
struct Edge
{
	int from, to, cost;
}e[Max];
int n, m, c[Max];
int father[Max];
int ans, minn = 0x3f3f3f3f;
bool cmp(Edge &a,Edge &b)
{
	return a.cost < b.cost;
}
int find(int x)
{
	if (father[x] == x) return x;
	return father[x] = find(father[x]);
}
int main()
{
	scanf("%d%d", &n,&m);
	for (int i = 1; i <= n; i++)
	{
		scanf("%d", c + i);
		father[i] = i;
		minn = min(minn, c[i]);
	}
	for (int i = 1; i <= m; i++)
	{
		scanf("%d%d%d", &e[i].from, &e[i].to, &e[i].cost);
		e[i].cost = 2 * e[i].cost + c[e[i].from] + c[e[i].to];
	}
	sort(e + 1, e + m + 1, cmp);
	for (int i = 1; i <= m; i++)
	{
		int fx = find(e[i].from);
		int fy = find(e[i].to);
		if (fx != fy)
		{
			father[fx] = fy;
			ans += e[i].cost;
		}
	}
	printf("%d\n", ans + minn);
	return 0;
}



  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值