import math
def calculate_distance(p):
if len(p) == 0:
return len(p)
else:
x = [i[0] for i in p]
y = [i[1]for i in p]
dist = 0
distx = 0
disty = 0
for i in range(len(x)):
x1 = x[i-1]
x2 = x[i]
distx = (x1-x2)**2
for v in range(len(y)):
y1 = y[v-1]
y2 = y[v]
disty = (y1-y2)**2
for j in p:
dist = math.sqrt(distx disty)
return dist
calculate_distance([(2,2), (5,2), (9,2)])
This last line of code returns 4 when it should return 7 since the total distance that has been traveled is 7 units. What am I doing wrong in my code? I have to do this without any additional module.
CodePudding user response:
The error is that you are processing the values altogether. The values need to be processed two at a time and then the distances should be added. A simple solution would be:
def calculateAdjDistance(z):
#calculate distance between the two selected points
print(z)
x1 = z[0][0]
x2 = z[1][0]
y1 = z[0][1]
y2 = z[1][1]
return ((x1-x2)**2 (y1-y2)**2)**(1/2)
def calculate_distance(p):
dist = 0
if len(p) == 0:
return 0
else:
for i in range(0,len(p)-1):
#select two points at a time
dist = calculateAdjDistance([list(p[i]), list(p[i 1])])
#adding the calculated distance to the previous distance
return dist
print(calculate_distance([(2,2), (5,2), (9,2)]))
CodePudding user response:
I've rewritten your code using the highly optimized numpy and scipy modules:
import numpy as np
from typing import *
from scipy.spatial import distance
def calculate_distance(p: List[Tuple[int, int]])-> float:
if p is None or len(p) == 0: return 0
dists: np.ndarray = distance.cdist(p, p, 'euclidean')
return float(np.sum(np.diag(dists, 1)))
print(calculate_distance([(2,2), (5,2), (9,2)])) # prints 7.0, as expected
If you have any questions as to how this works, do not hesitate to ask. Click on any of the following links to read more about scipy.spatial.distance
, np.diag
, and np.sum
.