boost中dijkstra算法简单示例

来源:互联网 发布:淘宝购物券在哪里设置 编辑:程序博客网 时间:2024/06/05 17:38

         我们经常用dijkstra算法来计算最短路径,其原理可以参考http://en.wikipedia.org/wiki/Dijkstra%27s_algorithm.

       

         boost库也提供了它的实现,我们就以上图为准,利用boost库中dijkstra算法对其做一个简单的实现:

        

#include <iostream> #include<boost\graph\adjacency_list.hpp>#include<boost\graph\dijkstra_shortest_paths.hpp>typedef boost::adjacency_list < boost::listS, boost::vecS, boost::directedS, boost::no_property, boost::property < boost::edge_weight_t, unsigned long > > graph_t;typedef boost::graph_traits < graph_t >::vertex_descriptor vertex_descriptor;typedef boost::graph_traits < graph_t >::edge_descriptor edge_descriptor;#include<vector>using namespace std;//Node定义struct Node{int nId;       //Node编号};//Link定义struct Link{int nStartNodeId;     //起始Node编号int nEndNodeId;       //终止Node编号int nLength;          //Link的长度Link(int nSId,int nEId,int nLen){nStartNodeId=nSId;nEndNodeId=nEId;nLength=nLen;}};//获取路径经过结点的信息void GetPath(int fromId,int toId,vector<vertex_descriptor>& vPredecessor,std::string& strPath){vector<int> vecPath;while(fromId!=toId){vecPath.push_back(toId);//因为本例子的特殊性和自己很懒,所以可以直接取值toId = vPredecessor[toId];}vecPath.push_back(toId);vector<int>::reverse_iterator pIter = vecPath.rbegin();strPath="路径:";std::string strOperator="->";char c[20]={};for(;pIter!=vecPath.rend();pIter++){itoa(*pIter,c,10);if(*pIter!=fromId){strPath+=(strOperator+c);}else{strPath+=c;}}}int _tmain(int argc, _TCHAR* argv[]){//构造Node集合vector<Node> vecNodes;for(int i=1;i<=6;i++){Node nd;nd.nId = i;vecNodes.push_back(nd);}//构造Link集合vector<Link> vecLinks;Link lk(1,3,9);vecLinks.push_back(lk);Link lk1(1,2,7);vecLinks.push_back(lk1);Link lk2(1,6,14);vecLinks.push_back(lk2);Link lk3(2,4,15);vecLinks.push_back(lk3);Link lk4(2,3,10);vecLinks.push_back(lk4);Link lk5(3,4,11);vecLinks.push_back(lk5);Link lk6(3,6,2);vecLinks.push_back(lk6);Link lk7(6,5,9);vecLinks.push_back(lk7);Link lk8(4,5,6);vecLinks.push_back(lk8);//图定义graph_t g;g.clear();boost::property_map<graph_t, boost::edge_weight_t>::type pmpWeightmap = boost::get(boost::edge_weight, g);for(int i=0;i<vecLinks.size();i++){edge_descriptor edEdge;bool bInserted;//加入Link的起始和终止NodeIDboost::tie(edEdge,bInserted)=boost::add_edge(vecLinks[i].nStartNodeId,vecLinks[i].nEndNodeId,g);//加入Link的长度pmpWeightmap[edEdge]=vecLinks[i].nLength;}//路径计算结果定义vector<vertex_descriptor> vPredecessor(boost::num_vertices(g));   //存储从起始结点到其他结点的路径上经过的最后一个中间结点序号vector<unsigned long> vDistance(boost::num_vertices(g));          //存储起始结点到其他结点的路径的距离//路径探索起始点定义vertex_descriptor s = boost::vertex(vecNodes[0].nId, g); //路径计算boost::property_map<graph_t, boost::vertex_index_t>::type pmpIndexmap = boost::get(boost::vertex_index, g);boost::dijkstra_shortest_paths(g, s, &vPredecessor[0], &vDistance[0], pmpWeightmap, pmpIndexmap,    std::less<unsigned long>(), boost::closed_plus<unsigned long>(),    std::numeric_limits<unsigned long>::max(), 0, boost::default_dijkstra_visitor());std::string strPath;GetPath(1,5,vPredecessor,strPath);cout<<strPath<<endl;cout<<"路径长度:"<<vDistance[5]<<endl;return 0;}