Вопрос
Как рассчитать евклидово расстояние между парой строк массива numpy Автор вопроса: Rashmi Singh 12.04.2017 Ответов: 3
У меня есть массив numpy, например:
import numpy as np
a = np.array([[1,0,1,0],
[1,1,0,0],
[1,0,1,0],
[0,0,1,1]])
Я хотел бы рассчитать euclidian distance между каждой парой строк.
from scipy.spatial import distance
for i in range(0,a.shape[0]):
d = [np.sqrt(np.sum((a[i]-a[j])**2)) for j in range(i+1,a.shape[0])]
print(d)
[1.4142135623730951, 0.0, 1.4142135623730951]
[1.4142135623730951, 2.0]
[1.4142135623730951]
[]
Есть ли лучший питонический способ сделать это, так как мне нужно запустить этот код на огромном массиве numpy?
Точки имеют произвольные размеры или всегда 4d? Willem Van Onsem 12.04.2017 Вы смотрели на : distance.pdist? Это должно решить это с помощью: distance.pdist(a). Каким должен быть конечный результат? Divakar 12.04.2017 @Divakar среди евклидовых расстояний между всеми парами векторов-строк Мне нужны k самых дальних векторов. Rashmi Singh 12.04.2017 @divakar Сэр, это сработало Rashmi Singh 12.04.2017 Также взгляните на KDTree - docs.scipy.org/doc/scipy-0.14.0/reference/generated/ Divakar 12.04.2017 python numpy euclidean-distance
Ответы Ответ 1 · рейтинг 10 · NaN
И для полноты, einsum часто используется для расчета расстояний.
a = np.array([[1,0,1,0],
[1,1,0,0],
[1,0,1,0],
[0,0,1,1]])
b = a.reshape(a.shape[0], 1, a.shape[1])
np.sqrt(np.einsum('ijk, ijk->ij', a-b, a-b))
array([[ 0. , 1.41421356, 0. , 1.41421356],
[ 1.41421356, 0. , 1.41421356, 2. ],
[ 0. , 1.41421356, 0. , 1.41421356],
[ 1.41421356, 2. , 1.41421356, 0. ]])
Ответ 2 · рейтинг 14 · comendeiro
С точки зрения чего-то более "элегантного", вы всегда можете использовать попарное евклидово расстояние scikitlearn:
from sklearn.metrics.pairwise import euclidean_distances
euclidean_distances(a,a)
с тем же выходом, что и один массив.
array([[ 0. , 1.41421356, 0. , 1.41421356],
[ 1.41421356, 0. , 1.41421356, 2. ],
[ 0. , 1.41421356, 0. , 1.41421356],
[ 1.41421356, 2. , 1.41421356, 0. ]])
Ответ 3 · Michael H.
Я использовал itertools.combinations вместе с np.linalg.norm разностного вектора (это евклидово расстояние):
import numpy as np
import itertools
a = np.array([[1,0,1,0],
[1,1,0,0],
[1,0,1,0],
[0,0,1,1]])
print([np.linalg.norm(x[0]-x[1]) for x in itertools.combinations(a, 2)])
Для понимания взгляните на этот пример из документов :combinations('ABCD', 2) дает AB AC AD BC BD CD. В вашем случае A, B, C и D являются строками вашей матрицы a, поэтому термин x[0]-x[1], появляющийся в приведенном выше коде, представляет собой разностный вектор векторов в строках a.
Перевод вопроса и ответов сообщества Stack Overflow, лицензия CC BY-SA. Оригинал на Stack Overflow .