EF Labs 代码挑战赛(步行的最短路径问题),草稿答案

地址:http://code-challenge.herokuapp.com/challenge/lost_in_jingan_temple

求到终点最短路径

不可以穿过建筑物,只能走建筑物之间的空间,可以斜着走;

起点是边界两点,终点是两直线交汇处.

以下是用用canvas画了示意图, 

EF Labs 代码挑战赛(步行的最短路径问题),草稿答案_第1张图片

算法:

主要数据结构:

两个栈,起点栈还有终点栈.

步骤:

  • 1.将起点,终点分别压入起点栈,终点栈
  • 2.从起点栈读取起点,终点栈读取终点,查找起点到终点的第一个障碍物,有跳转到第3步,没有跳转到第4步
  • 3.绕开障碍物
    • 3.1从左侧绕,确定下一个终点,将该终点压入终点栈,跳转步骤2
    • 3.2从右侧绕,确定下一个终点,将该终点压入终点栈,跳转步骤2
  • 4.终点栈出栈,起点栈入栈
  • 5.判断终点栈是否为空
    • 5.1终点栈为空,将起点栈加入候选路线,该分支结束
    • 5.2终点栈不为空,跳转步骤2

算法核心: 

红色字体标注部分,直接决定算法效率,准确性.

算法核心实现思路:

查找起点到终点的障碍物:

  • 1.根据起点终点坐标确定待搜索障碍物的范围

思路1:根据起点终点确定一个矩形框,如果障碍物有端点落在矩形框内,

将障碍物放入待搜索列表(沿起点到终点方向,按照框内端点顺序排列障碍物)

  • 2.确定路线上第一个碰到的障碍物(分解成更基本的问题是
判断两线段相交,如果路线与障碍物某条边相交,该障碍物在路线上)

思路1:根据线段确定直线求交点,判断交点是否在

其中一条线段上(交点坐标,在线段两点确定区间)

确定下一个终点:

  • 起点到终点连线将障碍物分成两半,下一个终点为起点限定的该多边行障碍物的切点
(两个,原来的起点终点连线两侧一边一个) 实现参考 http://topic.csdn.net/t/20030510/00/1763444.html ,

至于原因可以通过自己画图来理解,我数学不太好,可能用错词汇,

(就是以起点为顶点的扇形夹住多边型,接触的两个点,

如果接触的是一条边,取边远离顶点的端点为切点)

如果算法有错误,或者实现上有更好的思路,亦或是我忽略了某个重点步骤的实现,欢迎指正.

算法需要优化细节很多,没有时间,代码没有写.


补充:

之前算法遗漏了障碍物边挨着的情况,会导致结果错误.

解决办法两个: 

1.对于确定了一个终点时,终点压入起点栈,下一条路线遇到障碍物,且起点在障碍物的边上,需要对栈操作进行回滚,并对障碍物合并处理.

2.对地图数据进行预处理,将临边障碍物合并.

合并算法:确定一个矩形框,找到有点落在矩形框内的所有障碍物,对范围内所有边进行临边检查.找到了合并障碍物,进行下一区域临边检查.


    




你可能感兴趣的:(数据结构,算法,优化)