数据结构----单源最短路径Dijkstra
原理:参考趣学数据结构
代码:
stack.h 栈代码
# pragma once
# include <stdio.h>
# define maxSize 100
typedef struct stack { int * base; int * top;
} stack;
bool init ( stack & Stack) { Stack. base = new int [ maxSize] ; if ( ! Stack. base) { return false; } Stack. top = Stack. base; return true;
}
bool push ( stack & Stack, int e) { if ( Stack. top - Stack. base == maxSize) { return false; } * ( Stack. top) = e; Stack. top++ ; return true;
}
bool pop ( stack & Stack, int & e) { if ( Stack. base == Stack. top) { return false; } Stack. top-- ; e = * ( Stack. top) ; return true;
}
int getTop ( stack & Stack) { if ( Stack. base == Stack. top) { return - 1 ; } return * ( Stack. top - 1 ) ;
}
void printStack ( stack Stack) { while ( Stack. base != Stack. top) { printf ( "%d " , * ( Stack. top - 1 ) ) ; Stack. top-- ; }
}
bool empty ( stack Stack) { if ( Stack. base == Stack. top) { return true; } return false;
}
void testStack ( ) { stack Stack; init ( Stack) ; int value; while ( 1 ) { scanf_s ( "%d" , & value) ; if ( value == - 1 ) { break ; } push ( Stack, value) ; } printStack ( Stack) ;
}
dijkstra.cpp
# include <stdio.h>
# include <stdlib.h>
# include "stack.h"
# define N 100
# define elemType int
# define INF ( ( ( unsigned int ) ( - 1 ) ) >> 1 )
typedef struct GraphMatrix { elemType vNode[ N] [ N] ; int vNum, eNum;
} GraphMatrix;
void findPath ( GraphMatrix G, int dist[ ] , int p[ ] , int u, stack & Stack) ;
void initGMaxtix ( GraphMatrix & G) { printf ( "输入顶点数和边数\n" ) ; scanf_s ( "%d%d" , & G. vNum, & G. eNum) ; for ( int i = 0 ; i < G. vNum; i++ ) { for ( int j = 0 ; j < G. vNum; j++ ) { G. vNode[ i] [ j] = G. vNode[ j] [ i] = INF; } } printf ( "输入顶点v1到顶点v2和其边的权重\n" ) ; for ( int i = 0 ; i < G. eNum; i++ ) { int v1, v2, weights; scanf_s ( "%d%d%d" , & v1, & v2, & weights) ; G. vNode[ v1] [ v2] = G. vNode[ v2] [ v1] = weights; }
}
void print4 ( GraphMatrix G) { printf ( "邻接矩阵如下:\n" ) ; for ( int i = 0 ; i < G. vNum; i++ ) { for ( int j = 0 ; j < G. vNum; j++ ) { printf ( "%d " , G. vNode[ i] [ j] ) ; } printf ( "\n" ) ; }
}
void print41 ( int result[ ] , int length) { for ( int i = 0 ; i < length; i++ ) { printf ( "%d " , result[ i] ) ; } printf ( "\n" ) ;
}
void Dijkstra ( GraphMatrix G, int u) { bool flag[ N] ; int dist[ N] , p[ N] ; p[ u] = - 1 ; dist[ u] = 0 ; for ( int i = 0 ; i < G. vNum; i++ ) { flag[ i] = false; dist[ i] = G. vNode[ u] [ i] ; if ( G. vNode[ u] [ i] == INF) { p[ i] = - 1 ; } else { p[ i] = u; } } flag[ u] = true; for ( int i = 0 ; i < G. vNum - 1 ; i++ ) { int min= INF; int t= u; for ( int j = 0 ; j < G. vNum; j++ ) { if ( ! flag[ j] && dist[ j] < min) { t = j; min = dist[ j] ; } } if ( t == u) { break ; } flag[ t] = true; for ( int j = 0 ; j < G. vNum; j++ ) { if ( ! flag[ j] && dist[ t] + G. vNode[ t] [ j] < dist[ j] ) { dist[ j] = dist[ t] + G. vNode[ t] [ j] ; p[ j] = t; } } } stack Stack; init ( Stack) ; printf ( "输出单源最短路径的最优方案\n" ) ; findPath ( G, dist, p, u, Stack) ;
}
void findPath ( GraphMatrix G, int dist[ ] , int p[ ] , int u, stack & Stack) { for ( int i = 0 ; i < G. vNum; i++ ) { if ( p[ i] == - 1 ) { printf ( "%d---%d不可达!\n" , u, i) ; continue ; } push ( Stack, i) ; int x = p[ i] ; while ( x != - 1 ) { push ( Stack, x) ; x = p[ x] ; } int e; while ( ! empty ( Stack) ) { printf ( "%d" , getTop ( Stack) ) ; pop ( Stack, e) ; if ( Stack. top - Stack. base >= 1 ) { printf ( "---" ) ; } } printf ( " 这段路径的距离为:%d\n" , dist[ i] ) ; }
}
int main ( ) { GraphMatrix G; initGMaxtix ( G) ; print4 ( G) ; printf ( "\n" ) ; Dijkstra ( G, 0 ) ; system ( "pause" ) ; return 0 ;
}
测试截图:
时间复杂度为O(n),空间复杂度为O(n)!
如果存在什么问题,欢迎批评指正!谢谢!