UVA 1395 - Slim Span
题意:给定一些结点和边,要求出最苗条度最小的生成树,苗条度定义为:生成树中最大权的边减去最小权的边的值
思路:类似建最小生成树的算法,多一步枚举起始边即可
代码:
#include <cstdio> #include <cstring> #include <algorithm> using namespace std; const int N = 105; const int INF = 0x3f3f3f3f; int n, m, parent[N]; struct Edge { int u, v, val; Edge() {} Edge(int u, int v, int val) { this->u = u; this->v = v; this->val= val; } void read() { scanf("%d%d%d", &u, &v, &val); } } e[N * N]; int find(int x) { return x == parent[x] ? x : parent[x] = find(parent[x]); } bool cmp(Edge a, Edge b) { return a.val < b.val; } int main() { while (~scanf("%d%d", &n, &m) && n || m) { for (int i = 0; i < m; i++) e[i].read(); sort(e, e + m, cmp); int ans = INF; for (int i = 0; i < m; i++) { int cnt = 1; for (int j = 1; j <= n; j++) parent[j] = j; int flag = 1; for (int j = i; j < m; j++) { int u = find(e[j].u); int v = find(e[j].v); if (u != v) { parent[u] = v; cnt++; } if (cnt == n) { ans = min(ans, e[j].val - e[i].val); flag = 0; break; } } if (flag) break; } if (ans == INF) ans = -1; printf("%d\n", ans); } return 0; }
时间: 2024-11-25 09:48:48