zoukankan      html  css  js  c++  java
  • 关于单源最短路径的问题

    在此之前一直在看图算法,但是看的多了不免会有些混淆,今天我就算是进行一次自我总结吧。

    单源最短路径算法1:Dijkstra 算法

    这个算法是处理单元最短路径问题的,他的本质是一种贪心算法。

    实现: 

    将图G中所有的顶点V分成两个顶点集合S和T。以v为源点已经确定了最短路径的终点并入S集合中,S初始时只含顶点v,T则是尚未确定到源点v最短路径的顶点集合。然后每次从T集合中选择S集合点中到T路径最短的那个点,并加入到集合S中,并把这个点从集合T删除。直到T集合为空为止。
    具体步骤
    1、选一顶点v为源点,并视从源点v出发的所有边为到各顶点的最短路径(确定数据结构:因为求的是最短路径,所以①就要用一个记录从源点v到其它各顶点的路径长度数组dist[],开始时,dist是源点v到顶点i的直接边长度,即dist中记录的是邻接阵的第v行。②设一个用来记录从源点到其它顶点的路径数组path[],path中存放路径上第i个顶点的前驱顶点)。
    2、在上述的最短路径dist[]中选一条最短的,并将其终点(即<v,k>)k加入到集合s中。
    3、调整T中各顶点到源点v的最短路径。 因为当顶点k加入到集合s中后,源点v到T中剩余的其它顶点j就又增加了经过顶点k到达j的路径,这条路径可能要比源点v到j原来的最短的还要短。调整方法是比较dist[k]+g[k,j]与dist[j],取其中的较小者。
    4、再选出一个到源点v路径长度最小的顶点k,从T中删去后加入S中,再回去到第三步,如此重复,直到集合S中的包含图G的所有顶点。

      

    代码的实现:

    int cost[MAX_V][MAX_V] ;//cost[u][v]表示边e=(u,v)的权值
    int d[MAX_V] ;//顶点S出发的最短距离
    bool used[MAX_V] ;//已经使用过的点
    int V ;//顶点数
    void dijkstra(int s)
    {
        fill(d,d+V,INF);
        fill(used,used+V,false);
        d[s]=0;
        while(true)
        {
            int v=-1;
            for(int u=0;u<V;u++)
            {
                if(!used[u]&&(v==-1||d[u]<d[v]))
                v=u;
            }
            if(v==-1)    break;
            used[v]=true;
            for(int u=0;u<V;u++)
            {
                d[u]=min(d[u],d[v]+cost[v][u]);
            }
        }
    }

    下面是利用优先队列实现的

    struct edge{
        int to,cost;
    };
    typedef pair<int,int> P;
    int V;
    vector<edge>G[MAX_N];
    int d[MAX_N];
    void dijkstra(int s)
    {
        priority_queue<P,vector<P>,greater<P> > que;
        fill(d,d+v,INF);
        d[s]=0;
        que.push(P(0,s));
        while(!que.empty())
        {
            P p=que.top();que.pop();
            int v=p.second;
            if(d[v]<p.first)    continue;
            for(int i=0;i<G[v].size();i++)
            {
                edge e=G[v][i];
                if(d[e.to]>d[v]+e.cost)
                {
                    d[e.to]=d[v]+e.cost;
                    que.push(P(d[e.to],e.to));
                }
            }
        }
    }

    单源最短路径算法2 Bellman-Ford:

      由于dijkstra算法不能处理带有负数权值变得问题,所以还要学会一种能够处理负数权值边问题

      这个算法算是一种动态规划算法。

    struct edge{
        int from,to,cost;
    };
    edge es[MAX_N];
    int d[MAX_N];
    int V,E;
    void short_path(int s)
    {
        for(int i=0;i<V;i++)    d[i]=INF;
        d[s]=0;
        while(true)
        {
            bool update=false;
            for(int i=0;i<E;i++)
            {
                edge e=es[i];
                if(d[e.from]!=INF&&d[e.to]>e.cost+d[e.from])
                {
                    d[e.to]=e.cost+d[e.from];
                    update=true;
                }
            }
            if(!update)    break;
        }
    }
  • 相关阅读:
    java中<> 的用法
    Java 中 compareTo方法问题
    class AClass<E extends Comparable>与class AClass<E extends Comaprable<E>>有什么区别?
    zookeeper常用命令
    Storm概念讲解和工作原理介绍
    Storm集群安装部署步骤【详细版】
    Error contacting service. It is probably not running.
    Exception in thread "main" expected '<document start>', but found BlockMappingStart in 'reader', line 23, column 2: nimbus.host: "master"
    zookeeper 启动失败 BindException: Address already in use 或者Error contacting service. It is probably not running
    scss的安装使用
  • 原文地址:https://www.cnblogs.com/acmblog/p/9600628.html
Copyright © 2011-2022 走看看