hdu 1233 还是畅通工程 解题报告
2024-09-19 18:55:46
题目链接:http://code.hdu.edu.cn/showproblem.php?pid=1233
并查集的运用, 实质就是求最小生成树。先对所有的村庄距离从小到大排序,然后判断村庄之间是否属于同一集合,不是则将距离相加。属于同一集合,说明村庄连成了环,就不符合树的定义了。这样扫描下来,就求得最小生成树了。
要特别注意的是,数组越界问题。这个得益于Dwylkz的指点。由于村庄最多假设为100,为了防止边数越界,数组应该开到100 * 100 (10000)左右。
#include <iostream>
#include <algorithm>
using namespace std; const int maxn = + ; // 100个村庄边数最多为10000
struct sets
{
int v1, v2; // v1,v2分别表示村庄1和村庄2
int value; // 保存两村庄间的距离
} test[maxn]; int set[maxn]; // 保存集合中的代表 int cmp(sets a, sets b)
{
return a.value < b.value;
} int find(int x)
{
return x == set[x] ? x : find(set[x]);
} int main()
{
int a, b, i, n, cnt;
while (scanf("%d", &n) != EOF && n)
{
for (i = ; i <= n; i++)
{
set[i] = i; // 初始化为n个不相交的集合
}
int len = n * (n-) / ; // 输入的行数
for (i = ; i < len; i++)
{
scanf("%d%d%d", &test[i].v1, &test[i].v2, &test[i].value);
}
sort(test, test+len, cmp); // 对距离从小到大排序
for (cnt = i = ; i < len; i++)
{
a = find(test[i].v1);
b = find(test[i].v2);
if (a != b) // 不属于同一集合,则将距离相加,这个已保证能得到最小生成树
{
set[a] = b;
cnt += test[i].value;
}
}
printf("%d\n", cnt);
}
return ;
}
最新文章
- 多线程同步工具——LockSupport
- iis日志查看
- linux下搭建php的集成环境
- 深入理解JS的delete
- nVivo highlight code中的文本
- IE6、7绝对定位层被遮挡的原因(主要是父层决定的)
- 手把手教你在Windows下使用MinGW编译libav(参考libx264的编入)
- js实现windows扫雷(jquery)
- Android Intent的几种使用方法全面总结
- Linux C语言遍历目录结构
- MySql 日期转字符串
- linux路由表配置
- Harris角点检测算原理
- MAC vim安装gruvbox主题
- 记一次Java Core Dump分析过程
- Java输入输出小结
- C++学习 内存模型和名称空间
- 多张报表导出到一个多sheet页excel
- Bing词典vs有道词典比对测试报告
- Java CST格式字符串转换成Date类型的数据
热门文章
- 【Gym 100015A】Another Rock-Paper-Scissors Problem
- 与Java Web Service相关的若干概念(JAX-WS,JAX-RS)
- PL/0编译器(java version)&ndash;Praser.java
- linux在线学习
- Activator.CreateInstance 反射实例化对象
- C++标准转换运算符reinterpret_cast
- Matalab IFS分形算法
- dao、domain、service、web、vo、Model这些层的功能是什么
- GTP V0 和 GTP V1
- <;转>;Npoi导入导出Excel操作<;载>;