Shortest Way--dijkstra
This time write I use Dijkstra algorithm to do single source the shortest circuit experience.
First introduce a problem: give you two number m,n. N stands for a total of n villages. Then there are m lines, each line containing three number from,to,dist. These three numbers represent a long distance from the village to the village to the Dist, which is a graph of the absence of a map.
Now want to know how much the shortest path from village 1 to village N is.
Related Topics here http://poj.org/problem?id=2387
The first writing is a very simple Dijkstra algorithm: the adjacency matrix (two-dimensional array) to save the map, the outer for 1->n; and then first find the dist[] array inside the smallest number of numbers (representing the shortest distance from the destination to this numbered village). This number can be defined as the shortest path from the starting point to this number. The distance from the other villages to the starting point is then changed by using a for-1>n; to pass this shortest distance.
This is the core idea of the Dijkstra algorithm, the latter optimization is only the optimized data structure, the idea is not optimized.
An initial dist[] array holds the initial distance from the starting point to any point.
To give a simple example, it has been determined that the shortest distance from the village 1 to the Village 2 is 100, that the distance from the village 2 to the Village 3 is 100, from the village 1 to The distance of the village 3 is 500;
Then the distance from the 1->3 (500) can be changed from 1->2->3 (200), which is called the relaxation edge. But if the 1->2>3 is greater than the 1->3 distance, the edge does not have to be slack.
Look directly at the code:
<strong> #include <stdio.h> #include <algorithm> #include <string.h> #include <queue> using namespace Std;const int inf=0x3f3f3f3f; Maximum value, which is 1061109567int main () {int m,n; while (~SCANF ("%d%d", &m,&n)) {int fro,to,d; int a[n+2][n+2]; adjacency matrix map int dist[n+2],vist[n+2]; memset (A,inf,sizeof (a)); INF available memset memset (vist,0,sizeof (vist)); memset (dist,inf,sizeof (Dist)); dist[1]=0; for (int i=0; i<m; i++) {scanf ("%d%d%d", &fro,&to,&d); A[fro][to]=a[to][fro]=min (D,a[to][fro]); } for (int i=1; i<=n; i++) {int max1=inf; int x; Find the shortest path to loosen the other side for (int y=1; y<=n; y++) if (!VIST[Y]&&DIST[Y]<=MAX1) Max1=dist[x=y]; The vist[x]=1;//tag has found the shortest path from the starting point to the number X, and the next time no longer accesses · for (int y=1; y<=n; y++) {//slack edge operation if (!vist[y]& &dist[y]>dist[x]+a[x][y]) dist[y]=dist[x]+a[x][y]; }} printf ("%d\n", Dist[n]); }}</strong>
then see the book said can use priority queue, to find the shortest road. Priority queue: A queue in which an automatic sort operation is performed at the same time that it is queued, specifying the priority, where the smallest value in the dist[] array is found in a small priority.
#include <stdio.h> #include <algorithm> #include <string.h> #include <queue>using namespace std const int Inf=0x3f3f3f3f;struct node{//dis refers to the distance in the array of dist[], Num refers to the village number int dis,num; constructor, easy to assign initial value node (int dis1,int num1):d is (dis1), num (NUM1) {}//Specify priority, with small precedence bool operator < (const node &a) const {return dis>a.dis; }};int a[1003][1006];int vist[100000];int d[100000];int main () {int n,m; while (~SCANF ("%d%d", &m,&n)) {int fro,to,w; Priority_queue<node> Q; memset (A,inf,sizeof (a)); memset (vist,0,sizeof (vist)); Memset (d,inf,sizeof (d)); d[1]=0; for (int i=0; i<m; i++) {scanf ("%d%d%d", &fro,&to,&w); To the heavy side a[fro][to]=a[to][fro]=min (W,a[to][fro]); }//The contents of dist[1] are stored in the node structure and pressed into the priority queue Q.push (node (0,1)); while (!q.empty ()) {node tmp=q.top (); Q.pop (); int USubstituting x in the first code, which is the number int u=tmp.num with the smallest path; if (Vist[u]) continue; Vist[u]=1; for (int i=1;i<=n;i++) {if (D[i]>d[u]+a[i][u]) {d[i]=d[u]+a[ I][u]; Q.push (Node (d[i],i)); }}} printf ("%d\n", D[n]); }}
But the above is also flawed, that is, the storage of the graph is too small, can only store more than 1000 villages between the interrelationship, such as a[1005][1005], and if the sparse map, it is too wasted space and time. Then write a Dijkstra algorithm that uses vector arrays to simulate adjacency tables to store graphs.
Vector: A dynamically allocated space, called a dynamic array, defines it vector<int> G. There are three main modes of operation: 1): G.clear ();//emptying 2) g.size ();//Table Length 3) g.push_back ();// Add an element to the end of a table
The following code is given:
#include <iostream> #include <vector> #include <cstring> #include <stdio.h> #include <queue > #include <algorithm>using namespace std;const int inf=0x3f3f3f3f;const int max=10000;struct edge//save edge {int T O,dist; constructor, you can assign the initial edge (int to1=0,int dist1=0): to (to1), dist (dist1) {}};struct node//into queue {int num,dist; Node (int num1=0,int dist1=0): num (NUM1), dist (DIST1) {} BOOL operator < (const node &a) Const {return D ist>a.dist; }};vector<edge> g[max];inline void Addedge (int fro,int to, int dis) {//non-direction graph, the forward graph discards the second statement g[fro].push_back (Edge (to , dis)); G[to].push_back (Edge (Fro,dis));} int m,n;int vist[max],dist[max];void Dijkstra (int start) {for (int i=1; i<=n; i++) {dist[i]=inf; vist[i]=0; } dist[start]=0; priority_queue<node>q; Q.push (Node (start,0)); node tmp; while (!q.empty ()) {tmp=q.top (); Q.pop (); U refers to the x in the first code, that is, the number with the smallest path, int u=tmp.num; The marker has found the shortest path from the starting point to the number X, and the next time no longer accesses · if (Vist[u]) continue; Vist[u]=1; The shortest path to the village U has been found, below to loosen the edge for (int i=0; i<g[u].size (); i++) {//with FF) that can be optimized by U-Village to reduce code complexity EDG E &ff=G[u][i]; if (dist[ff.to]>dist[u]+ff.dist) {dist[ff.to]=dist[u]+ff.dist; Q.push (Node (ff.to,dist[ff.to)); }}}}int A[max],b[max],c[max];int main () {while (scanf ("%d%d", &m,&n)!=eof) {for (int i=0;i& lt;=n;i++) g[i].clear (); You must use the empty function because there are loops and global variables. for (int i=0; i<m; i++) scanf ("%d%d%d", &a[i],&b[i],&c[i]); deposited in the adjacency table for (int i=0; i<m; i++) Addedge (A[i],b[i],c[i]); The starting point is one Dijkstra (1); printf ("%d\n", Dist[n]); }}
Copyright NOTICE: This article for Bo Master original article, without Bo Master permission not reproduced.
Shortest Way--dijkstra