Build a minimal-cost network, the most primitive of the minimum spanning tree applications.
This is solved using the union find and Kruskal algorithms.
Attention:
1 The data given is the original matrix, but it needs to be converted into a graph of the side representation, so that the Kruskal can be used easily because the sort
2 Reduce the edge, a matrix needs (N*n-n) >>1 Edge, some people discuss whether the question is directed, it is meaningless, because the smallest spanning tree and direction is irrelevant.
3 The Union find is used to determine if there is a ring, much faster than the original judgment.
#include <stdio.h> #include <stdlib.h>const int max_vec = 101;int n;//number of verticesstruct subset{int p, RA NK;}; struct Edge{int src, des, Wei;}; struct Graph{int V, E; Edge *edge; Graph (int v, int e): V (v), E (e) {edge = new edge[e];} ~graph () {if (edge) delete[]edge; edge = NULL;}}; static int cmp (const void *a, const void *b) {Edge *A1 = (edge *) A; Edge *B1 = (Edge *) B;return A1->wei-b1->wei;} Subset *subs; Edge *res; Graph *gra;void Initresource () {subs = new Subset[n];for (int i = 0; i < N; i++) {subs[i].p = I;subs[i].rank = 0;} res = new edge[n-1];} inline void Releaseresource () {if (subs) Delete [] subs;if (RES) Delete [] res;} int find (int node) {if (SUBS[NODE].P! = node) SUBS[NODE].P = Find (SUBS[NODE].P); return SUBS[NODE].P;} inline void Uniontwo (int x, int y) {int xroot = find (x); int yroot = find (y); if (Subs[xroot].rank < Subs[yroot].rank) Sub S[XROOT].P = Yroot;else if (Subs[xroot].rank > Subs[yroot].rank) subs[yroot].p = xroot;else{subs[xroot].rank++;subs[ Yroot].p = Xroot;}} int mst () {initresource (); Qsort (Gra->edge, gra->e, sizeof (EDGE), CMP); for (int i = 0, v = 0; i < gra->e &&A mp V < gra->v-1; i++) {int xroot = find (GRA->EDGE[I].SRC), int yroot = Find (Gra->edge[i].des), if (xroot! = yroot) {uniontwo (Xroot, Yroot); res[v++] = Gra->edge[i];}} int ans = 0;for (int i = 0; i < N-1; i++) {ans + = Res[i].wei;} Releaseresource (); return ans;} int main () {int w;while (~scanf ("%d", &n)) {gra = new Graph (N, (n*n-n) >>1); int e = 0;for (int i = 0; i < N; i++ {for (int j = 0, J < N, J + +) {scanf ("%d", &w), if (J <= i) continue;//the value of the lower triangle is not in the edge GRA->EDGE[E].SRC = i;gra->ed Ge[e].des = J;gra->edge[e++].wei = w;}} printf ("%d\n", MST ());d elete Gra;} return 0;}