问题如下,
我会得到一组长绳的x和y坐标(大约30到4万的坐标数组)。绳子躺在地上,可以是任何形状。
现在我将获得一个起点(基本上是x和y坐标)和一个终点。
从上面提到的坐标数组中确定x和y坐标集的有效方法是在起点和终点之间。
详尽的搜索,即循环40k次是不可接受的解决方案(在问题文件中提到)
错误的一点余地是可以接受的
答案 0 :(得分:4)
我们需要找到数组中的起点,然后是终点。对于每一个,我们可以将绳索视为描述距离该点的距离函数,并且我们正在寻找该距离图上的最低点。如果一个点距离很远而另一个点非常接近,我们可以做一些插值猜测下一步搜索的位置。
distance
| /---\
|-- \ /\ -
| -- ------- -- ------ ---------- -
| \ / \---/ \--/
+-----------------------X--------------------------- array index
在上面的表示中,我们想找到“X”......我们看几个点的距离,得到距离曲线的斜率,甚至可能是该斜率的变化率,帮助指导我们下一步的探索......
为了完善在我们知道距离值较低的区域进行二元搜索或插值搜索的基本方法,我们可以使用以下方法:
否则,总是存在风险,目标点可能奇怪地被两个非常远的点包围,令我们的整个搜索算法受挫(这必然是他们对错误的一些余地的意思 - 时不时这个搜索将不得不恢复到O(N)暴力搜索,因为任何趋势分析都失败了。)
答案 1 :(得分:0)
对于一次性搜索,有时线性遍历是最简单,最快速的解决方案。也许这就是这个问题的原因。
遍历有序的点列表,直到找到开始或结束,然后收集点直到达到另一个端点。
现在,如果我们希望重复搜索,我们可以建立点的索引。
编辑:除了@koool提到的限制外,没有任何其他限制。约束点之间的距离将允许在@Tony的答案中描述的爬山方法。
答案 2 :(得分:0)
我认为你不能使用穷举搜索以外的任何东西来准确地解决它。比如说绳索被折成两半的情况下,所产生的双绳形成一个螺旋形,两端位于中心。
然而,如果我们假设绳索的长部分是直线的,那么我们可以根据斜率检查消除很多点:
if (abs(slope(x[i],y[i],x[i+1],y[i+1])
-slope(x[i+1],y[i+1],x[i+2],y[i+2]))<tolerance)
eliminate (x[i+1],y[i+1]);
如果绳索的大部分是直线的话,这将显着缩短搜索时间。但是将是线性WRT剩余点数。
答案 3 :(得分:0)
所以基本上,你有一个包含整个绳索的点的排序列表,你从该列表中得到两个任意点,并负责返回这两个点之间存在的子列表。
我将假设所提供的起点和终点与分类列表中的点完全一致(否则会引入许多问题,特别是如果绳索可能任意薄而且通过多次开始/结束点)。
这意味着你真正想要的只是两个提供坐标的索引。或索引为1,答案为“是右边还是左边的第二个坐标?”。
简单的O(n)解决方案是:
For each index in array
coord = array[index]
if (coord == point1)
startIndex = index
if (coord == point2)
endIndex = index
if (endIndex < startIndex)
swap(startIndex, endIndex)
return array.sublist(startIndex, endIndex)
或者,如果您想针对重复查询进行优化,我建议使用基于散列的方法,将每个coordinate映射到数组中的索引。类似的东西:
//build the map (do this once, at init)
map = {}
For each index in array
coord = array[index]
map[coord] = index
//find a sublist (do this for each set of start/end points)
startIndex = map[point1]
endIndex = map[point2]
if (endIndex < startIndex)
swap(startIndex, endIndex)
return array.sublist(startIndex, endIndex)
构建地图的是O(n),但是一旦构建了地图,就可以确定O(1)中任意两点之间的子列表。当然,假设有效的hashmap。
请注意,如果我的假设不成立,那么相同的解决方案仍然可用,前提是作为第一步,您可以获取提供的起点和终点,并找到阵列中与每个点最佳对应的点。如上所述,除非您对绳索的厚度有一些限制,否则从任意坐标插入到实际上是绳索的一部分只能猜测最多。