比赛 |
2025暑期集训第8场 |
评测结果 |
AAAAATTTTT |
题目名称 |
次小生成树 |
最终得分 |
50 |
用户昵称 |
对立猫猫对立 |
运行时间 |
10.069 s |
代码语言 |
C++ |
内存使用 |
7.39 MiB |
提交时间 |
2025-08-13 11:17:09 |
显示代码纯文本
#include <bits/stdc++.h>
using namespace std;
typedef long long LL;
const LL INF = 1e18;
const int N = 100005, M = 5e5 + 5;
struct Edge {
int u, v, w;
bool used;
bool operator<(const Edge &e) const { return w < e.w; }
} edges[M];
int n, m, p[N];
vector<pair<int, int>> g[N];
int find(int x) {
return p[x] == x ? x : p[x] = find(p[x]);
}
LL kruskal() {
sort(edges, edges + m);
for (int i = 1; i <= n; i++) p[i] = i;
LL res = 0;
for (int i = 0; i < m; i++) {
int u = edges[i].u, v = edges[i].v, w = edges[i].w;
int pu = find(u), pv = find(v);
if (pu != pv) {
p[pu] = pv;
res += w;
edges[i].used = true;
g[u].emplace_back(v, w);
g[v].emplace_back(u, w);
}
}
return res;
}
void dfs(int u, int fa, LL maxd1, LL maxd2, int target, LL &res1, LL &res2) {
if (u == target) {
res1 = maxd1;
res2 = maxd2;
return;
}
for (auto a : g[u]) {
int v = a.first, w = a.second;
if (v == fa) continue;
LL td1 = maxd1, td2 = maxd2;
if (w > td1) td2 = td1, td1 = w;
else if (w < td1 && w > td2) td2 = w;
dfs(v, u, td1, td2, target, res1, res2);
}
}
LL get_second_mst() {
LL mst = kruskal();
LL res = INF;
for (int i = 0; i < m; i++) {
if (!edges[i].used) {
int u = edges[i].u, v = edges[i].v, w = edges[i].w;
LL max1 = -INF, max2 = -INF;
dfs(u, -1, -INF, -INF, v, max1, max2);
if (w > max1) res = min(res, mst + w - max1);
else if (w > max2) res = min(res, mst + w - max2);
}
}
return res;
}
int main() {
freopen("secmst.in", "r", stdin);
freopen("secmst.out", "w", stdout);
cin >> n >> m;
for (int i = 0; i < m; i++) {
cin >> edges[i].u >> edges[i].v >> edges[i].w;
edges[i].used = false;
}
LL ans = get_second_mst();
cout << ans << endl;
return 0;
}