简体   繁体   English

python - 给定两个元组列表找到它们之间最接近的元组(dist

[英]python - given two tuples lists find the closest tuple between them (dist

I have two lists with tuples (coordinates), for example: 我有两个带元组(坐标)的列表,例如:

some_pt1 = [(10.76,2.9),(3.24,4.28),(7.98,1.98),(3.21,9.87)]
some_pt2 = [(11.87,6.87), (67.87,8.88), (44.44, 6.78), (9.81, 1.09), (6.91, 0.56), (8.76, 8.97), (8.21, 71.66)]
  • each value in the tuples is a flat 元组中的每个值都是平坦的
  • the lists are not in the same length 列表长度不一样

I what to find the two closest points between the two lists. 我在两个列表之间找到两个最接近的点。 I don't know how, maybe it is possible to do it using distances. 我不知道怎么样,也许有可能用距离来做。 I hope there is a more efficient way to do this cause I need this function to work as fast as possible (it is a part of something bigger). 我希望有一种更有效的方法来做到这一点,因为我需要这个功能尽可能快地工作(它是更大的一部分)。

Alternatively, by taking reference Tim Seed's code. 或者,通过参考Tim Seed的代码。 this can be used. 这可以用。

from scipy.spatial import distance
some_pt1 = [(10.76,2.9),(3.24,4.28),(7.98,1.98),(3.21,9.87)]
some_pt2 = [(11.87,6.87), (67.87,8.88), (44.44, 6.78), (9.81, 1.09), (6.91, 0.56), (8.76, 8.97), (8.21, 71.66)]

empthy_dict = {}
for i in range(len(some_pt1)):
    for j in range(len(some_pt2)):
        dist = distance.euclidean(some_pt1[i],some_pt2[j])
        empthy_dict[dist] = [some_pt1[i],some_pt2[j]]

shortest = sorted(empthy_dict.keys())[0]
points = empthy_dict[shortest]
print('Shortest distance is ' ,shortest,' and points are ' ,points)

How about this 这个怎么样

from pprint import pprint

some_pt1 = [(10.76,2.9),(3.24,4.28),(7.98,1.98),(3.21,9.87)]
some_pt2 = [(11.87,6.87), (67.87,8.88), (44.44, 6.78), (9.81, 1.09), (6.91, 0.56), (8.76, 8.97), (8.21, 71.66)]


distance = {}
for x in some_pt1:
    for y in some_pt2:
        dist =abs(abs(x[0])-abs(y[0]))+abs(abs(x[1])-abs(y[1]))
        distance[dist]=[x,y]

shortest =sorted(distance.keys())[0]
print("Min Distance is {} Objects are  {} {} ".format(shortest, distance[shortest][0],distance[shortest][0]))

In any case you need to do all posible combinations, there are algorithms out there that can help you do it in the best order or avoiding repeating distances. 在任何情况下,您都需要做所有可能的组合,有一些算法可以帮助您以最佳顺序执行或避免重复距离。 If you want to do it fast you should use a special library that helps compiling with the or precompiling the arrays, this could be done with Numba or Cython . 如果你想快速完成它,你应该使用一个特殊的库来帮助编译或预编译数组,这可以用NumbaCython来完成。 Other libraries such as scipy have special modules suh as scipy.spatial.distance . 其他库如scipy有特殊模块,如scipy.spatial.distance Look at this post for more doubts similar cuestion . 看看这篇文章,可以更多地怀疑类似的猜测

Example: 例:

import scipy.spatial.distance as sd
import numpy as np
some_pt1 = [(10.76,2.9),(3.24,4.28),(7.98,1.98),(3.21,9.87)]
some_pt2 = [(11.87,6.87), (67.87,8.88), (44.44, 6.78), (9.81, 1.09), (6.91, 0.56), (8.76, 8.97), (8.21, 71.66)]
np.unravel_index(np.argmin(sd.cdist(some_pt1, some_pt2)), (len(some_pt1), len(some_pt2)))

results: (2, 4) 结果: (2, 4)

This code would return the position in the first list and in the second. 此代码将返回第一个列表和第二个列表中的位置。

By Euclidian distance: 按欧几里得距离:

>>> some_pt1 = [(10.76,2.9),(3.24,4.28),(7.98,1.98),(3.21,9.87)]
>>> some_pt2 = [(11.87,6.87), (67.87,8.88), (44.44, 6.78), (9.81, 1.09), (6.91, 0.56), (8.76, 8.97), (8.21, 71.66)]
>>> 
>>> def dist_sq(p1_p2):
...     p1, p2 = p1_p2
...     return sum(x*y for x,y in zip(p1, p2))
... 
>>> 
>>> min(((p1, p2) for p1 in some_pt1 for p2 in some_pt2), key=dist_sq)
((3.24, 4.28), (6.91, 0.56))

Which has runtime O(n*m) (where n, m are the lengths of your lists). 其中有运行时O(n * m)(其中n,m是列表的长度)。 Since you need to look at all the pairs, it won't get better than this. 既然你需要查看所有对,那么它将不会比这更好。

Note that comparing the squared distances is enough, no need to compute the root. 请注意,比较平方距离就足够了,不需要计算根。

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM