最大数据集中2个点之间的距离并识别点

时间:2015-07-28 03:51:36

标签: python matlab numpy

我有一个由几个点的x,y,z坐标组成的矩阵。我想找到极值点,即最远的两个点。

我可以在matlab中找到一种方法,但我需要它在Python中

这是matlab中的代码

A = randint(500,3,[-5 5]);
D=pdist(A);
D=squareform(D);
[N,I]=max(D(:));
[I_row, I_col] = ind2sub(size(D),I);

pdist给出点对之间的距离(i,j)。 squareform给出矩阵输出 在最后两个步骤中,我尝试找到矩阵I_row,I_col ..

的索引

点I_row和I_col有最大距离..

任何人都可以在python中建议我一个有效的方法,因为我所有的其他代码都是用Python编写的。

4 个答案:

答案 0 :(得分:5)

这里所有其他答案都花费 O(N ^ 2)的时间和空间。太可怕了。

相反,要认识到数据集中的两个最远点位于集合的凸包上。由于可以在3D中以 O(N log N)时间计算船体,因此可以形成有效的预过滤器。在我对具有16,000,000点的数据集的测试中,凸包仅包含420点。

可以在 O(H log H)时间找到船体上最远的点,尽管这在Python中很难实现。因此,我们可以在那时转回 O(N ^ 2) cdist解决方案。

import numpy as np
from scipy.spatial import ConvexHull
from scipy.spatial.distance import cdist

N = 16000000

# Find a convex hull in O(N log N)
points = np.random.rand(N, 3)   # N random points in 3-D

# Returned 420 points in testing
hull = ConvexHull(points)

# Extract the points forming the hull
hullpoints = points[hull.vertices,:]

# Naive way of finding the best pair in O(H^2) time if H is number of points on
# hull
hdist = cdist(hullpoints, hullpoints, metric='euclidean')

# Get the farthest apart points
bestpair = np.unravel_index(hdist.argmax(), hdist.shape)

#Print them
print([hullpoints[bestpair[0]],hullpoints[bestpair[1]]])

答案 1 :(得分:4)

如果你有scipy,那么对于大多数matlab核心函数你都具有相同的等价物:

from numpy import random, nanmax, argmax, unravel_index
from scipy.spatial.distance import pdist, squareform

A = random.randint(-5,5, (500,3))
D = pdist(A)
D = squareform(D);
N, [I_row, I_col] = nanmax(D), unravel_index( argmax(D), D.shape )

你也可以使用itertools

在纯python中获取它
from itertools import combinations
from random import randint

A = [[randint(-5,5) for coord in range(3)] for point in range(500)]

def square_distance(x,y): return sum([(xi-yi)**2 for xi, yi in zip(x,y)])    

max_square_distance = 0
for pair in combinations(A,2):
    if square_distance(*pair) > max_square_distance:
        max_square_distance = square_distance(*pair)
        max_pair = pair

答案 2 :(得分:3)

这将为您提供A中与temp_b相距最远的点的索引对。请注意,它将包括列表中的两个方向,例如(8,222)和(222,8)。如果你愿意,我会留给你删除它们。

import numpy as np
import random as rd
from scipy.spatial.distance import pdist
from scipy.spatial.distance import squareform

A = np.array([np.array([rd.randint(-5,5) for x in range(3)]) for y in range(500)])
D=pdist(A)
D=squareform(D)
temp = np.where(D == D.max())
temp_b = zip(temp[0],temp[1])

答案 3 :(得分:0)

您可以使用scipy的pdist

import numpy as np
from scipy.spatial.distance import pdist, squareform
A = np.random.randint(-5, 5, [500, 3])
D = squareform(pdist(A))
N = np.max(D)
I = np.argmax(D)
I_row, I_col = np.unravel_index(I, D.shape)