算法笔记_070-BellmanFord算法简单介绍(Java)

转载 2017年03月20日 14:59:27

目录

1 问题描述

2 解决方案

2.1 具体编码

 


1 问题描述

何为BellmanFord算法?

BellmanFord算法功能:给定一个加权连通图,选取一个顶点,称为起点,求取起点到其它所有顶点之间的最短距离,其显著特点是可以求取含负权图的单源最短路径

BellmanFord算法思想:

  • 第一,初始化所有点。每一个点保存一个值,表示从原点到达这个点的距离,将原点的值设为0,其它的点的值设为无穷大(表示不可达)。
  • 第二,进行循环,循环下标为从1n1n等于图中点的个数)。在循环内部,遍历所有的边,进行松弛计算。
  • 第三,遍历途中所有的边(edgeuv)),判断是否存在这样情况:如果dv> d (u) + w(u,v),则返回false,表示途中存在从源点可达的权为负的回路。

 


2 解决方案

2.1 具体编码

Bellman-Ford算法寻找单源最短路径的时间复杂度为O(V*E)。(V为给定图的顶点集合,E为给定图的边集合)

本文编码思想主要参考自文末参考资料1中博客,想要进一步了解,可以参考文末参考资料。

首先看下代码中所使用的连通图(PS:改图为无向连通图,所以每两个顶点之间均有两条边):

 

现在求取顶点A到其它所有顶点之间的最短距离

具体代码如下:

package com.liuzhen.chapter9;

import java.util.Scanner;

public class BellmanFord {
    
    public  long[] result;       //用于存放第0个顶点到其它顶点之间的最短距离
    
    //内部类,表示图的一条加权边
    class edge {
        public int a;   //边的起点
        public int b;   //边的终点
        public int value;  //边的权值
        
        edge(int a, int b, int value) {
            this.a = a;
            this.b = b;
            this.value = value;
        }
    }
    //返回第0个顶点到其它所有顶点之间的最短距离
    public  boolean getShortestPaths(int n, edge[] A) {
        result = new long[n];
        for(int i = 1;i < n;i++)
            result[i] = Integer.MAX_VALUE;  //初始化第0个顶点到其它顶点之间的距离为无穷大,此处用Integer型最大值表示
        for(int i = 1;i < n;i++) {
            for(int j = 0;j < A.length;j++) {
                if(result[A[j].b] > result[A[j].a] + A[j].value)
                    result[A[j].b] = result[A[j].a] + A[j].value;
            }
        }
        boolean judge = true;
        for(int i = 1;i < n;i++) {   //判断给定图中是否存在负环
            if(result[A[i].b] > result[A[i].a] + A[i].value) {
                judge = false;
                break;
            }
        }
        return judge;
    }
    
    public static void main(String[] args) {
        BellmanFord test = new BellmanFord();
        Scanner in = new Scanner(System.in);
        System.out.println("请输入一个图的顶点总数n和边总数p:");
        int n = in.nextInt();
        int p = in.nextInt();
        edge[] A = new edge[p];
        System.out.println("请输入具体边的数据:");
        for(int i = 0;i < p;i++) {
            int a = in.nextInt();
            int b = in.nextInt();
            int value = in.nextInt();
            A[i] = test.new edge(a, b, value);
        }
        if(test.getShortestPaths(n, A)) {
            for(int i = 0;i < test.result.length;i++)
                System.out.print(test.result[i]+" ");
        } else
            System.out.println("给定图存在负环,没有最短距离");
    }
    
}

运行结果:

请输入一个图的顶点总数n和边总数p:
6 18
请输入具体边的数据:
0 1 6
0 2 3
1 2 2
1 3 5
2 3 3
2 4 4
3 4 2
3 5 3
4 5 5
1 0 6
2 0 3
2 1 2
3 1 5
3 2 3
4 2 4
4 3 2
5 3 3
5 4 5
0 5 3 6 7 9 

 

 

参考资料:

1.bellman ford 算法

[算法系列之二十九]Bellman-Ford最短路径算法

单源最短路径给定一个图,和一个源顶点src,找到从src到其它所有所有顶点的最短路径,图中可能含有负权值的边。Dijksra的算法是一个贪婪算法,时间复杂度是O(VLogV)(使用最小堆)。但是迪杰斯...
  • SunnyYoona
  • SunnyYoona
  • 2015年04月23日 15:15
  • 3857

Bellman-Ford算法详讲

Dijkstra算法是处理单源最短路径的有效算法,但它局限于边的权值非负的情况,若图中出现权值为负的边,Dijkstra算法就会失效,求出的最短路径就可能是错的。 这时候,就需要使用其他的算法来求解最...
  • niushuai666
  • niushuai666
  • 2011年09月19日 21:56
  • 51697

Dijkstra、Bellman-Ford及Spfa算法思想对比

Dijkstradijkstra算法本质上算是贪心的思想,每次在剩余节点中找到离起点最近的节点放到队列中,并用来更新剩下的节点的距离,再将它标记上表示已经找到到它的最短路径,以后不用更新它了。这样做的...
  • mmy1996
  • mmy1996
  • 2016年08月16日 23:10
  • 5758

浅谈路径规划算法之Bellman-Ford算法

最近在研究AGV系统的调度算法,为了实现多AGV小车的运行,给每一个AGV小车规划一条最优路径,对比了Bellman-Ford算法、SPFA算法、Dijkstra算法、Floyd算法和A*算法的优缺点...
  • AK_Lady
  • AK_Lady
  • 2017年04月12日 20:35
  • 910

最短路径算法(2)—Bellman-Ford(贝尔曼-福特)算法

Source: http://www.wutianqi.com/?p=1912
  • c8481892
  • c8481892
  • 2016年09月20日 14:47
  • 554

最短路径(三)—Bellman-Ford算法(解决负权边)

前两节我们写了Floyd-Warshall算法http://blog.csdn.net/wtyvhreal/article/details/43315705和 Dijkstra算法http://bl...
  • wtyvhreal
  • wtyvhreal
  • 2015年02月03日 15:45
  • 4049

单源最短路径之Bellman-Ford算法

今天介绍一种计算单源最短路径的算法Bellman-Ford算法,对于图G=(V,E)来说,该算法的时间复杂度为O(VE),其中V是顶点数,E是边数。Bellman-Ford算法适用于任何有向图,并能报...
  • Ivan_zgj
  • Ivan_zgj
  • 2016年06月01日 13:19
  • 1366

bellman ford 算法 判断是否存在负环

Flyer 目录视图摘要视图订阅 微信小程序实战项目——点餐系统        程序员11月书讯,评论得书啦        ...
  • hang__xiu2016acm
  • hang__xiu2016acm
  • 2016年11月26日 21:19
  • 1758

Bellman-Ford算法

转自:http://www.wutianqi.com/?p=1912 Dijkstra算法是处理单源最短路径的有效算法,但它局限于边的权值非负的情况,若图中出现权值为负的边,Dijkstra算法...
  • Tsaid
  • Tsaid
  • 2011年10月08日 21:09
  • 7605

Bellman-ford算法与Dijkstra算法(RIP和OSPF的基本算法)

这里讨论下RIP和OSPF的基本算法,在CISCO课程中讨论RIP和OSPF的区别有不少,但是回溯源头,它们理论算法里面的原理差不多,比较大的区别主要有三点 1.Bellman-ford的链路距...
  • u012116229
  • u012116229
  • 2015年03月10日 19:17
  • 1630
内容举报
返回顶部
收藏助手
不良信息举报
您举报文章:算法笔记_070-BellmanFord算法简单介绍(Java)
举报原因:
原因补充:

(最多只允许输入30个字)