There are two pieces of code together Here:
One
This piece of code is comprehensive, and it's a reference to the relevant source code on GITHUB.
able to say Powerful.
Dijkstra (dijkstra algorithm) #include <stdio.h> #include <stdlib.h> #include <string.h> #define MAX 100 Matrix Maximum Capacity # define INF 65535//maximum 65535#define isletter (a) (((a) >= ' a ') && ((a) <= ' z ') ) || (((a) >= ' A ') && ((a) <= ' Z '))) #define LENGTH (a) (sizeof (a)/sizeof (a[0))//the adjacency matrix of the graph stores typedef struct _GRAPH{CHAR vexs[max]; Vertex set int vexnum; Vertex number int edgnum; Number of sides int matrix[max][max]; Adjacency matrix}graph, structure of *pgraph;//side typedef struct _EDGEDATA{CHAR start;//edge start char end; End of Edge int weight; The weight of the edge}edata;/* * Returns the position of ch in matrix matrices */static int get_position (Graph G, char ch) {int i; For (i=0; i<g.vexnum; I++) if (g.vexs[i]==ch) return i; return-1;} /* * Read an input character */static char Read_char () {char ch; Do {ch = GetChar (); } while (!isletter (ch)); Return ch;} /* * Create diagram (own input) */graph* create_graph () {char c1, c2; int v, e; int i, j, Weight, p1, p2; graph* pG; Enter the number of vertices and the number of sides printf (please Enter the number of vertices: \ n); scanf ("%d", &v); printf ("please Enter the number of sides: \ n"); scanf ("%d", &e); If (v < 1 | | E < 1 | | (e > (v * (v-1)))) {printf ("wrong input!!
!\n "); Return NULL; } if ((pg= (graph*) malloc (sizeof)) = = Null) return null; memset (pG, 0, sizeof);//initialize//initialize "vertex number" and "number of sides" pg->vexnum = v; Pg->edgnum = e; Initialize "vertex" for (i = 0; i < pg->vexnum; i++) {printf ("vertex (%d):", i); pg->vexs[i] = Read_char (); }//1. Initialize the "edge" weights for (i = 0; i < pg->vexnum; i++) {for (j = 0; J < pg->vexnum; J + +) { If (i==j) pg->matrix[i][j] = 0; else pg->matrix[i][j] = INF; }}//2. Initialize the "edge" weights: initialize for (i = 0; i < pg->edgnum; i++) {//read The starting vertex of the edge, end vertex, weight printf ("edge (%d)") According to the User's input: ", i); C1 = Read_char (); C2 = Read_char (); scanf ("%d", &weight); P1 = get_position (*pg, c1); P2 = get_position (*pg, c2); If (p1==-1 | | p2==-1) {printf ("input error!!! \ n "); Free (pG); Return NULL; } pg->matrix[p1][p2] = weight; pg->matrix[p2][p1] = weight; } return pG;} /* * Create diagram (with provided matrix) */graph* create_example_graph () {char vexs[] = {' A ', ' B ', ' C ', ' D ', ' E ', ' F ', ' G '}; int matrix[][9] = {/*a*//*b*//*c*//*d*//*e*//*f*//*g*//*a*/{0, 14, inf, inf, inf, 16,}, /*b*/{0, inf, inf, 7, inf},/*c*/{inf, 0, 3, 5, 6, inf},/*d*/{inf, inf, 3, 0, 4, inf, inf},/*e*/{inf, inf, 5, 4, 0, 2, 8},/*f*/{7, 6, INF, 2, 0, 9}, /*g*/{+, inf, inf, inf, 8, 9, 0}}; int Vlen = LENGTH (vexs); int i, j; graph* pG; Enter the number of vertices and the number of edges if (pg= (graph*) malloc (sizeof) = = Null) return null; memset (pG, 0, sizeof (Graph)); Initialize "vertex count" pg->vexnum = vlen; Initialize "vertex" for (i = 0; i < pg->vexnum; i++) pg->vexs[i] = vexs[i]; Initialize "edge" for (i = 0; i < pg->vexnum; i++) For (j = 0; J < pg->vexnum; j + +) pg->matrix[i][j] = matrix[i][j]; Count the number of edges for (i = 0; i < pg->vexnum; i++) for (j = 0; J < pg->vexnum; J + +) if (i!=j & ;& Pg->matrix[i][j]!=inf) pg->edgnum++; Pg->edgnum/= 2; Return pG;} /* returns the index of the first adjacency vertex of the vertex v. Failure is returned-1 */static int first_vertex (Graph G, int v) {int i; If (v<0 | | v> (g.vexnum-1)) return-1; For (i = 0; I < g.vexnum; i++) if (g.matrix[v][i]!=0 && g.matrix[v][i]!=inf) return i; return-1;} /* * Returns the index of vertex v relative to the next adjacency vertex of w, and fails returns 1 */static int Next_vertix (Graph G, int v, int W) {int i; If (v<0 | | v> (g.vexnum-1) | | w<0 | | w> (g.vexnum-1)) return-1; For (i = w + 1; i < g.vexnum; i++) if (g.matrix[v][i]!=0 && g.matrix[v][i]!=inf) return i; return-1;} /* * Depth-first Search Traversal graph recursive implementation */static void DFS (Graph G, int i, int *visited) { int w; visited[i] = 1; printf ("%c", g.vexs[i]); Iterates through all the adjacency vertices of the Vertex. If you haven't interviewed Me. So keep going down for (w = First_vertex (g, i); w >= 0; w = Next_vertix (g, i, w)) {if (!visited[w]) DFS (g , w, visited); }}/* * Depth First search traverse graph */void dfstraverse (graph G) {int i; int visited[max]; Vertex access mark//initialize All vertices are not interviewed for (i = 0; i < g.vexnum; i++) visited[i] = 0; printf ("DFS:"); For (i = 0; i < g.vexnum; i++) {//printf ("\n== LOOP (%d) \ n", i); If (!visited[i]) DFS (G, i, visited); } printf ("\ n");} /* Breadth-first Search (similar to Tree-level traversal) */void BFS (Graph G) {int head = 0; int rear = 0; int queue[max]; Auxiliary Group Queue int visited[max]; Vertex access Mark int i, j, k; For (i = 0; i < g.vexnum; i++) visited[i] = 0; printf ("BFS:"); For (i = 0; i < g.vexnum; i++) {if (!visited[i]) {visited[i] = 1; printf ("%c", g.vexs[i]); queue[rear++] = i; Into the queue} while (head! = Rear) {j = queue[head++]; Out queue for (k = First_vertex (g, j); k >= 0; k = Next_vertix (g, j, k))//k is an access adjacency vertex { If (!visited[k]) {visited[k] = 1; printf ("%c", g.vexs[k]); queue[rear++] = k; }}}} printf ("\ n");} /* * Print matrix queue graph */void print_graph (graph G) {int i,j; printf ("martix graph:\n"); For (i = 0; i < g.vexnum; i++) {for (j = 0; J < g.vexnum; J + +) printf ("%10d", g.matrix[i][j]) ; printf ("\ n"); }}/* * Prim minimum spanning tree * * parameter description: * G--adjacency matrix * start-the start element begins. Generate minimum tree */void prim (Graph G, int start) {int min,i,j,k,m,n,sum; int index=0; Prim index of the smallest tree, which is the index of the prims array char prims[max]; Prim of the smallest tree result array int weights[max]; The weight of the edge between Vertices//prim the first number in the minimum spanning tree is "start of the first vertex in the graph", because it starts from Start. prims[index++] = G.vexs[start]; Initialize the weights array for vertices,//to initialize the weights of each vertex to the "start vertex" to "the vertex" weight.
For (i = 0; i < g.vexnum; i++) weights[i] = g.matrix[start][i]; Initializes the weight value of the first vertex to 0. Can be understood as "the distance of the first vertex to itself is 0".
weights[start] = 0; For (i = 0; i < g.vexnum; i++) {//because starting from start, there is no need to process the first Vertex. if (start = = I) continue; j = 0; K = 0; Min = INF; In vertices that have not been added to the minimum spanning tree. Find the vertex with the least weight.
While (j < G.vexnum) {//if weights[j]=0. means that the "J node has been sorted" (or has been added to the minimum spanning tree). If (weights[j]! = 0 && weights[j] < min) {min = weights[j]; K = j; } j + +; }//after processing above, The least-weighted vertex is the K-vertex in the vertices that are not added to the minimum spanning tree. Add the K vertex to the result array of the smallest spanning tree prims[index++] = g.vexs[k]; Mark the weight of the K vertex as 0. means that the K-vertex has been sorted (or has been added to the minimum tree result). weights[k] = 0; When the K-vertex is added to the result array of the smallest spanning tree, the weights of the other vertices are updated. For (j = 0; J < g.vexnum; J + +) {//when The J node is not processed and needs to be updated.
If (weights[j]! = 0 && g.matrix[k][j] < weights[j]) weights[j] = g.matrix[k][j]; }}//calculate the weight of the minimum spanning tree sum = 0; For (i = 1; i < index; i++) {min = INF; Get prims[i] position in G n = get_position (G, prims[i]); In vexs[0...i], find the vertex with the smallest weight of J. For (j = 0; J < i; j + +) {m = get_position (G, prims[j]); If (g.matrix[m][n]<min) min = g.matrix[m][n]; } Sum + = min; }//print minimum Spanning tree printf ("PRIM (%c) =%d:", g.vexs[start], sum); For (i = 0; i < index; i++) printf ("%c", prims[i]); printf ("\ n");} /* * Get the Edge */edata* get_edges (graph G) {int i,j in the graph; int index=0; EData *edges; edges = (edata*) malloc (g.edgnum*sizeof (EData)); For (i=0;i < G.vexnum;i++) {for (j=i+1;j < G.vexnum;j++) {if (g.matrix[i][j]!=inf) {edges[index].start = g.vexs[i]; EdgeS[index].end = g.vexs[j]; Edges[index].weight = g.matrix[i][j]; index++; }}} return edges;} /* * Sort the edges according to the weights (from Small to Large) */void sorted_edges (edata* edges, int elen) {int i,j; For (i=0, i<elen; i++) {for (j=i+1; j<elen; j + +) {if (edges[i].weight > Edges[j].we Ight) {//exchange "i-edge" and "j-side" EData tmp = edges[i]; edges[i] = edges[j]; edges[j] = tmp; }}}}/* * Gets the end of I */int get_end (int vends[], int i) {while (vends[i]! = 0) i = vends[i]; Return i;} /* * Kruskal (kruskal) minimum spanning tree */void Kruskal (Graph G) {int i,m,n,p1,p2; int length; int index = 0; Index of the rets array int vends[max]={0}; Used to save the end point of each vertex in the existing minimum spanning tree in the smallest tree. EData rets[max]; The result array, preserving the edge EData *edges of the Kruskal minimum spanning tree; All sides of the graph Corresponding//get "all sides of the graph" edges = get_edges (G); Sort the edges according to the size of "weight" (from small to Large) sorted_edges (edges, g.edgnum); For (i=0; i<g.edgnum; i++) {p1 = get_position (G, edges[i].start); Gets the ordinal number of the "start" of the edge of the P2 = get_position (G, edges[i].end); Gets the ordinal number m = Get_end (vends, p1) of the "end point" of the section I edge; Gets the end point of P1 in the "existing minimum spanning tree" n = get_end (vends, p2); Gets the end point of the P2 in the "existing minimum spanning tree"//assumes m!=n, meaning that "edge i" and "vertices that have been added to the minimum spanning tree" do not form a loop if (m! = N) {vends[m] = n ; Set m at the end of "existing minimum spanning tree" to n rets[index++] = edges[i]; Save results}} Free (edges); Statistics and printing of "kruskal minimum spanning tree" information length = 0; For (i = 0; i < index; i++) length + = rets[i].weight; printf ("kruskal=%d:", length); For (i = 0; i < index; i++) printf ("(%c,%c)", rets[i].start, rets[i].end); printf ("\ n");} /* * Dijkstra Shortest path. * That is, the shortest path of the "vertex vs" to each of the other vertices in the chart (G).
* * parameters: * G--figure * vs--start vertex (start vertex). That is, the shortest path of vertex vs to other vertices is computed. * Prev--the predecessor Vertex array. That The value of prev[i] is the vertex in all vertices experienced by the shortest path of vertex vs to Vertex i, which is before Vertex I. * Dist--length Array. That Dist[i] is the length of the shortest path for vertex vs to Vertex I. */void Dijkstra (Graph G, int vs, int prev[], int Dist[]) {int i,j,k; int min; int tmp; int flag[max]; Flag[i]=1 indicates that the shortest path to vertex vs to Vertex I has been successfully obtained. Initialize for (i = 0; i < g.vexnum; i++) {flag[i] = 0; The shortest path to vertex i is not yet available. prev[i] = 0; The predecessor vertex of vertex i is 0.
dist[i] = g.matrix[vs][i];//the Shortest path to vertex i is the right of "vertex vs" to "vertex i".
}//initialize "vertex vs" itself flag[vs] = 1; dist[vs] = 0; Traverse G.vexnum-1 times, and find the shortest path of a vertex at a Time. For (i = 1; i < g.vexnum; i++) {//find the current smallest path;//. In the vertices that do not get the shortest path, find the closest to vs recent Vertex (k).
min = INF; For (j = 0; J < g.vexnum; j + +) {if (flag[j]==0 && Dist[j]<min) { Min = dist[j]; K = j; }}//mark "vertex k" for already acquired to shortest path flag[k] = 1; Fix the current shortest path and precursor vertex//i.e., update the shortest path and precursor vertex for vertices that do not get the shortest path, when the shortest path to vertex k is Already. For (j = 0; J < g.vexnum; j + +) {tmp = (g.matrix[k][j]==inf?
)INF: (min + g.matrix[k][j])); Prevent overflow if (flag[j] = = 0 && (tmp < dist[j])) {dist[j] = tmp; prev[j] = k; }}}//print The result of Dijkstra shortest path printf ("dijkstra (%c): \ n", g.vexs[vs]); For (i = 0; i < g.vexnum; i++) printf ("shortest (%c,%c) =%d\n", g.vexs[vs], g.vexs[i], dist[i]);} int main () {int prev[max] = {0}; int dist[max] = {0}; graph* pG; Define yourself "graph" (input matrix QUEUE)//PG = Create_graph (); Using the existing "figure" PG = create_example_graph ();p rint_graph (*pg); Print Figure//dfstraverse (*pg); Depth-first Traversal OF//BFS (*pg); Breadth-first Traversal Of//prim (*pg, 0); The prim algorithm generates the minimum spanning Tree//kruskal (*pg); The Kruskal algorithm generates a minimum spanning Tree//dijkstra algorithm to obtain the shortest distance from "4th vertex" to each other vertex Dijkstra (*pg, 3, prev, dist); return 0;}
Result Diagram:
Two
This is a simpler, relatively good understanding.
#include <stdio.h> #include <stdlib.h> #define MAX 1000000int arcs[10][10];//adjacency Matrix int d[10];//save Shortest path length int p[ 10][10];//path int final[10];//if final[i] = 1 indicates that vertex VI is already in the set S int n = 0;//vertex number int v0 = 0;//source point int v,w;void shortestpath_dij () {int i = 0, min = 0; For (v = 0; v < n; v++)//cyclic initialization {final[v] = 0; d[v] = arcs[v0][v]; For (w = 0; W < n; w++) p[v][w] = 0;//set empty path if (d[v] < MAX) {p[v][v0] = 1; p[v][v] = 1;} } d[v0] = 0; final[v0]=0; Initialize the V0 vertex belongs to the set S//start main loop each time v0 to a vertex v the shortest path and add V to the set S for (i = 1; i < n; i++) {min = MAX; For (w = 0; W < n; W++) {//i think the core process--point if (!final[w])//assuming w vertex in V-s {//the point at which this process is finally chosen should be to select the vertex in the current v-s that is associated with S//and the least weighted value in the book describing the current point if it is near V0. (d[w] < Min) {v = w; min = d[w];} }} final[v] = 1; Select the point to add to the collection s for (w = 0; W < n; w++)//update currentShortest path and distance {/* in this loop, v is the point in the collection s that is currently selected to see if the D0V+DVW is less than d[w] if the point v is the Midpoint. For example, add point 3 to investigate whether d[5] is to be updated to infer that D (v0-v3) + D (v3-v5) and whether it is less than d[5] */if (!final[w] && (min+ Arcs[v][w]<d[w]) {d[w] = min + arcs[v][w]; p[w] = p[v]; p[w][w] = 1; p[w] = p[v] + [w]}}}} int main () {int i, j; scanf ("%d", &n);//vertex number for (i = 0; i < n; i++) {for (j = 0; J < n; J + +) {SC ANF ("%d", &arcs[i][j]);//used to store adjacency matrix}} Shortestpath_dij (); For (i = 0; i < n; i++) printf ("d[%d] =%d\n", i,d[i]); Return 0;}
Results:
The Dijkstra (dijkstra) algorithm of the shortest path for the---c language of data structure