wen
wen

Reputation: 1935

How to use outer product to compute pairwise Euclidean distance in R

I have a matrix, where the first 10 rows are centroids and last 10 rows are points. I want to compute pairwise Euclidean distance.

mat = matrix(c(25,125, 44,105, 29,97,  35,63,  55,63, 
           42,57,  23,40,  64,37,  33,22,  55,20,
           28,145, 65,140, 50,130, 38,115, 55,118,
           50,90,  43,83,  63,88,  50,60, 50,30), 
           ncol=2, byrow=T)

centroids = mat[1:10,]
points = mat[11:20,]

eudis = function(x, y) { sqrt( sum( (x-y)^2 ) ) } # define Euclidean distance

I try to apply outer product like the following.

outer(centroids, points, FUN = eudis)

But it won't work. I thought I had success with outer product dealing with similar situations. Could someone make it work? Thanks in advance!

Upvotes: 1

Views: 872

Answers (1)

Matthew Lundberg
Matthew Lundberg

Reputation: 42649

I think you want a matrix showing the distance between each centroid and each point. To do that with outer you can iterate over the indices:

outer(1:10, 1:10, FUN=Vectorize(function(x, y) eudis(centroids[x,], points[y,])))
           [,1]      [,2]      [,3]     [,4]     [,5]     [,6]     [,7]     [,8]      [,9]    [,10]
 [1,]  20.22375  42.72002  25.49510 16.40122 30.80584 43.01163 45.69464 53.03772 69.641941 98.23441
 [2,]  43.08132  40.81666  25.70992 11.66190 17.02939 16.15549 22.02272 25.49510 45.398238 75.23962
 [3,]  48.01042  56.08030  39.11521 20.12461 33.42155 22.13594 19.79899 35.17101 42.544095 70.21396
 [4,]  82.29824  82.63776  68.65858 52.08647 58.52350 30.88689 21.54066 37.53665 15.297059 36.24914
 [5,]  86.33076  77.64664  67.18631 54.70832 55.00000 27.45906 23.32381 26.24881  5.830952 33.37664
 [6,]  89.10668  86.12781  73.43705 58.13777 62.36986 33.95585 26.01922 37.44329  8.544004 28.16026
 [7,] 105.11898 108.46197  93.96276 76.48529 84.30896 56.82429 47.42362 62.48200 33.600595 28.79236
 [8,] 113.84200 103.00485  94.04786 82.21922 81.49847 54.81788 50.56679 51.00980 26.925824 15.65248
 [9,] 123.10158 122.26201 109.32978 93.13431 98.48858 70.09280 61.81424 72.49828 41.629317 18.78829
[10,] 127.88276 120.41595 110.11358 96.50907 98.00000 70.17834 64.13267 68.46897 40.311289 11.18034

Indeed you need to vectorize the eudis function for this to work, as vectors are passed to the function by outer, but not in the way that eudis expects.

Upvotes: 4

Related Questions