Java用Dijkstra算法实现地图两点的最短路径查询(Android版)
地图上实现最短路径的查询,据我了解的,一般用Dijkstra算法和A*算法来实现。由于这是一个课程项目,时间比较急,而且自己不熟悉A*算法,所以参考网上的Dijkstra算法(http://blog.csdn.net/javaman_chen/article/details/8254309)的代码来实现了地图上任意两点的最短路径的查询。但该demo存在一个很严重的错误,缺了两行非常关键的代码……
首先,来了解下Dijkstra算法:无向图的最短路径求解算法之——Dijkstra算法 http://sbp810050504.blog.51cto.com/2799422/690803 。由此可以看出,Dijkstra算法的效率是很低的,它遍历的点很多,要以起始点为中心向外层层扩展,直到扩展到终点为止,所以数据量很少时不适合Dijkstra算法。处理该算法时,要特别注意在由一个点找到相邻该点最近点的时候,记得要将相邻的点的距离更新。
Dijkstra一般的表述通常有两种方式,一种用永久和临时标号方式,一种是用OPEN, CLOSE表的方式,这里是采用第二种方式,也就是采用的贪心法的算法策略,大概过程如下:
1.定义两个集合:open和close,open用于存储未遍历的节点,close用来存储已遍历的节点;
2.初始阶段,将初始节点放入close,其他所有节点放入open;
3.以初始节点为中心向外一层层遍历,获取离指定节点最近的子节点放入close并重新更新相邻点的距离,直至close包含所有子节点;
此方法由一个点遍历了其他所有点,所以可以知道该点到其他所有点的距离,时间复杂度很高。那个demo是一个一个数据初始化的,我将它改为用数组存储,然后用for循环来初始化,也就是将它封装成我需要的数据接口,并没有很大的优化。
算法核心只有两个函数:
/**
* 获取与node最近的子节点
*/
private Node getShortestPath(Node node) {
Node res = null;
int minDis = Integer.MAX_VALUE;
Map<Node, Integer> childs = node.getChild(); // 循环比较,找出离node最近的子节点
for (Node child : childs.keySet()) {
if (open.contains(child)) {
int distance = childs.get(child);
if (distance < minDis) {
minDis = distance;
res = child;
}
}
}
return res;
}
public void computePath(Node start) {
Node nearest = getShortestPath(start);// 取距离start节点最近的子节点,放入close
if (nearest == null) {
return;
}
close.add(nearest);
open.remove(nearest);
Map<Node, Integer> childs = nearest.getChild();
for (Node child : childs.keySet()) {
if (open.contains(child)) {// 如果子节点在open中
Integer newCompute = path.get(nearest.getName()) + childs.get(child);
if (path.get(child.getName()) > newCompute) {// 之前设置的距离大于新计算出来的距离
path.put(child.getName(), newCompute);
start.getChild().put(child, newCompute);
close.add(start);
pathInfo.put(child.getName(), pathInfo.get(nearest.getName()) + "-" + child.getName());
}
}
}
computePath(start);// 重复执行自己,确保所有子节点被遍历
computePath(nearest);// 向外一层层递归,直至所有顶点被遍历
}
那个demo漏了两行代码,就是找到最近的路径后,没有更新相邻点的距离
start.getChild().put(child, newCompute);
close.add(start);
这是一个Android平板的应用,代码在:http://pan.baidu.com/share/link?shareid=3275093017&uk=3726801344
还有很多东西没优化,欢迎指出,一起学习!
Java用Dijkstra算法实现地图两点的最短路径查询(Android版)的更多相关文章
- [算法] Dijkstra算法(带权有向图 最短路径算法)
一.带权有向图 二.算法原理 1)由于我们的节点是从1-6,所以我们创建的列表或数组都是n+1的长度,index=0的部分不使用,循环范围为1-6(方便计算). 2)循环之前,我们先初始化dis数组和 ...
- java 蓝桥杯算法提高 _1区间k大数查询
import java.util.Scanner; public class _1区间K大数查询 { public static void main(String[] args) { Scanner ...
- Java实现Dijkstra算法求最短路径
任务描述:在一个无向图中,获取起始节点到所有其他节点的最短路径描述 Dijkstra(迪杰斯特拉)算法是典型的最短路径路由算法,用于计算一个节点到其他所有节点的最短路径.主要特点是以起始点为中心向外层 ...
- JAVA实现DIJKSTRA算法
import java.util.Queue; import java.util.LinkedList; public class dijkstra{ public static void main( ...
- Dijkstra算法:任意两点间的最短路问题 路径还原
#define _CRT_SECURE_NO_WARNINGS /* 7 10 0 1 5 0 2 2 1 2 4 1 3 2 2 3 6 2 4 10 3 5 1 4 5 3 4 6 5 5 6 9 ...
- hdu 2544 最短路(两点间最短路径)
题目:http://acm.hdu.edu.cn/showproblem.php?pid=2544 方法一:dijkstra算法,求两点之间最短路径. /*********************** ...
- Dijkstra算法求最短路径(java)(转)
原文链接:Dijkstra算法求最短路径(java) 任务描述:在一个无向图中,获取起始节点到所有其他节点的最短路径描述 Dijkstra(迪杰斯特拉)算法是典型的最短路径路由算法,用于计算一个节点到 ...
- 数据结构与算法系列研究七——图、prim算法、dijkstra算法
图.prim算法.dijkstra算法 1. 图的定义 图(Graph)可以简单表示为G=<V, E>,其中V称为顶点(vertex)集合,E称为边(edge)集合.图论中的图(graph ...
- 求最短路径(Bellman-Ford算法与Dijkstra算法)
前言 Dijkstra算法是处理单源最短路径的有效算法,但它局限于边的权值非负的情况,若图中出现权值为负的边,Dijkstra算法就会失效,求出的最短路径就可能是错的.这时候,就需要使用其他的算法来求 ...
随机推荐
- leetcode算法刷题(三)
今天在刷了几道简单的动态规划后,又看了看string方面的题 第五题 Longest Palindromic Substring 题目的意思:求一个字符串的最长回文子串 分析:开始,我的想法是,现在字 ...
- select函数详解及应用
Select在Socket编程中还是比较重要的,可是对于初学Socket的人来说都不太爱用Select写程序,他们只是习惯写诸如connect. accept.recv或recvfrom这样的阻塞程序 ...
- Delphi之TDrawGrid绘制
一直都对QQ的好友列表很好奇,最先感觉用TreeView实现的,看了看TreeView的源码,发现要实现还真的不太好完成任务啊,其中最大的原因是自己的功力不足,后来觉得用ListView来做吧,结果也 ...
- Windows 10开发基础——文件、文件夹和库(一)
原文:Windows 10开发基础--文件.文件夹和库(一) 主要内容: 1.枚举查询文件和文件夹 2.文本文件读写的三种方法——创建写入和读取文件 3.获得文件的属性 枚举查询文件和文件夹 先了解一 ...
- docker 在esx上的网络配置
- 实用chrome插件
2015年最实用的9款chrome插件 随着14年chrome浏览器的市场超过IE浏览器,chrome凭借它强劲性能和出色的使用体验真正的登上了平民级的殿堂.今天小编就为大家推荐9款自己常用的chro ...
- StarTeam SDK 13 下载安装
SDK 13据称兼容 StarTeam 11. 下载地址是:ftp://us.ftp.microfocus.com/Starteam/st-sdk-13.0-readme.htm Java用户可以选在 ...
- 用Meta 取消流量器缓存实现每次访问都刷新页面方便调试
如果想禁止浏览器从本地缓存中调阅页面,可以设置网页不保存在缓存中,每次访问都刷新页面,下面是Meta在这方便的用法,需要的朋友可以参考下: <!-- 禁止浏览器从本地缓存中调阅页面.--> ...
- 最简单的视音频播放演示样例4:Direct3D播放RGB(通过Texture)
===================================================== 最简单的视音频播放演示样例系列文章列表: 最简单的视音频播放演示样例1:总述 最简单的视音频 ...
- data按钮
1.加载状态 通过按钮(Button)插件,您可以添加进一些交互,比如控制按钮状态,或者为其他组件(如工具栏)创建按钮组. 如需向按钮添加加载状态,只需要简单地向 button 元素添加 data-l ...