1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118
| #include <iostream> #include <cstdio> #include <algorithm> #include <cstring> #define MAXN 100005 #define MAXE 300005 #define LL long long #define INF 1e18 using namespace std;
int n, m, cnt, max1, max2, head[MAXN], f1[MAXN], f2[MAXN][25], dis[MAXN][25][2], dep[MAXN]; LL sum, ans=INF;
struct Edge {int x, y, dis; bool tag;} edge[MAXE]; struct Tree {int next, to, dis;} tree[MAXN*2];
bool CMP (Edge x, Edge y) {return x.dis<y.dis;}
int find(int x) { if(f1[x]!=x) f1[x]=find(f1[x]); return f1[x]; }
void addedge(int from, int to, int dis) { tree[++cnt].next=head[from]; tree[cnt].to=to; tree[cnt].dis=dis; head[from]=cnt; }
void kruskal() { for(int i=1; i<=n; i++) f1[i]=i; sort(edge+1, edge+m+1, CMP); for(int i=1; i<=m; i++) { int fx=find(edge[i].x), fy=find(edge[i].y); if(fx!=fy) { f1[fx]=fy; sum+=edge[i].dis; edge[i].tag=true; addedge(edge[i].x, edge[i].y, edge[i].dis); addedge(edge[i].y, edge[i].x, edge[i].dis); } } }
void dfs(int x, int fa) { f2[x][0]=fa; for(int i=head[x]; i; i=tree[i].next) { int to=tree[i].to; if(to==fa) continue; dis[to][0][0]=tree[i].dis; dep[to]=dep[x]+1; dfs(to, x); } }
void init() { for(int i=1; i<=20; i++) { for(int j=1; j<=n; j++) { f2[j][i]=f2[f2[j][i-1]][i-1]; dis[j][i][0]=max(dis[j][i-1][0], dis[f2[j][i-1]][i-1][0]); dis[j][i][1]=max(dis[j][i-1][1], dis[f2[j][i-1]][i-1][1]); if(dis[f2[j][i-1]][i-1][0]==dis[j][i-1][0]) continue; dis[j][i][1]=max(dis[j][i][1], min(dis[f2[j][i-1]][i-1][0], dis[j][i-1][0])); } } }
int Lca(int x, int y) { if(dep[x]<dep[y]) swap(x, y); for(int i=20; i>=0; i--) if(dep[f2[x][i]]>=dep[y]) x=f2[x][i]; if(x==y) return x; for(int i=20; i>=0; i--) if(f2[x][i]!=f2[y][i]) x=f2[x][i], y=f2[y][i]; return f2[x][0]; }
int solve(int x, int y, int len) { int maxn=0; for(int i=20; i>=0; i--) { if(dep[f2[x][i]]>=dep[y]) { if(dis[x][i][0]==len) maxn=max(maxn, dis[x][i][1]); else maxn=max(maxn, dis[x][i][0]); x=f2[x][i]; } } return maxn; }
int main() { scanf("%d%d", &n, &m); for(int i=1; i<=m; i++) scanf("%d%d%d", &edge[i].x, &edge[i].y, &edge[i].dis); kruskal(); dfs(1, 0); init(); for(int i=1; i<=m; i++) { if(edge[i].tag) continue; int lca=Lca(edge[i].x, edge[i].y); max1=solve(edge[i].x, lca, edge[i].dis); max2=solve(edge[i].y, lca, edge[i].dis); ans=min(ans, sum-max(max1, max2)+edge[i].dis); } printf("%lld\n", ans); }
|