博客
关于我
强烈建议你试试无所不能的chatGPT,快点击我
构造完全图
阅读量:5118 次
发布时间:2019-06-13

本文共 1499 字,大约阅读时间需要 4 分钟。

 

由于我好久都没有独立思考了(抄了好久题解),思维什么的早没有了。

看完题只能想到一种暴力:遍历+LCA

题目给出的是一个最小生成树,我们可以从边入手,把每条边所连的左右两个点分别看做一个集合,

左边集合和右边集合所要连的边数是(cnt[i]*cnt[j]-1),-1是因为要抛去本身这条边

我们要连的边权是多大?比当前的边大,

否则就不满足有且仅有一棵最小生成树T,所以边权就为(当前边的边权+1)

我们可以贪心的去解决,把边从小到大排序,并查集一下就行了,当然还得加上原始边的边权。

另外...ans的开long long

#include
#include
#define ll long longusing namespace std;inline int read(){ int sum = 0,p = 1; char ch = getchar(); while(ch < '0' || ch > '9') { if(ch == '-') p = -1; ch = getchar(); } while(ch >= '0' && ch <= '9') { (sum *= 10) += ch - '0'; ch = getchar(); } return sum * p;}const int N = 1e5 + 5;int n,fa[N],cnt[N];ll ans;struct edge{ int frm,to,wei;}e[N];bool cmp(edge a,edge b){ return a.wei < b.wei;}int findfa(int x){ return fa[x] == x ? x : findfa(fa[x]);} void kruskal(){ for(int i = 1;i <= n;i++) { fa[i] = i; cnt[i] = 1; } sort(e+1,e+n,cmp); for(int i = 1;i <= n - 1;i++) { int u = findfa(e[i].frm); int v = findfa(e[i].to); if(u == v) continue; fa[v] = u; ans += (ll)(cnt[u] * cnt[v] - 1) * (e[i].wei + 1); cnt[u] += cnt[v]; }}int main(){ n = read(); for(int i = 1;i <= n - 1;i++) { e[i].frm = read(); e[i].to = read(); e[i].wei = read(); ans += (ll)e[i].wei; } kruskal(); printf("%lld",ans); return 0;}
View Code

 

转载于:https://www.cnblogs.com/darlingroot/p/11282065.html

你可能感兴趣的文章
关于TFS2010使用常见问题
查看>>
聚合与组合
查看>>
ionic2+ 基础
查看>>
Screening technology proved cost effective deal
查看>>
【2.2】创建博客文章模型
查看>>
Jsp抓取页面内容
查看>>
大三上学期软件工程作业之点餐系统(网页版)的一些心得
查看>>
Java语言概述
查看>>
关于BOM知识的整理
查看>>
使用word发布博客
查看>>
微服务之初了解(一)
查看>>
GDOI DAY1游记
查看>>
MyBaits动态sql语句
查看>>
HDU4405(期望DP)
查看>>
拉格朗日乘子法 那些年学过的高数
查看>>
vs code 的便捷使用
查看>>
Spring MVC @ResponseBody返回中文字符串乱码问题
查看>>
用户空间与内核空间,进程上下文与中断上下文[总结]
查看>>
JS 中的跨域请求
查看>>
JAVA开发环境搭建
查看>>