An existing function to calculate 2 coordinates. for example, it can calculate the distance between this 2 cities (52.22, 21.01) and (52.40, 16.92).
from math import sin, cos, sqrt, atan2, radians
def cor_dist_calculator(lat1, lat2, lon1, lon2):
R = 6373.0
dlon = lon2 - lon1
dlat = lat2 - lat1
a = sin(dlat / 2)**2 + cos(lat1) * cos(lat2) * sin(dlon / 2)**2
c = 2 * atan2(sqrt(a), sqrt(1 - a))
distance = R * c
print "Distance is: " + str(distance) + " km."
return
# to calcualte distance between (52.22, 21.01) and (52.40, 16.92)
cor_dist_calculator(radians(52.22), radians(52.40), radians(21.01), radians(16.92))
The output is:
Distance is: 278.82127298 km.
Now for a list of cities, I want to calculate the distances between any 2 of them. The data comes in a dictionary form, and I can access the coordinates:
cities = {
"Ahmedabad":"23.02579,72.58727",
"Bengaluru":"12.97194,77.59369",
"Chennai":"13.08784,80.27847",
"Delhi":"28.65195,77.23149",
"Hyderabad":"17.38405,78.45636",
"Kanpur":"26.46523,80.34975",
"Kolkata":"22.56263,88.36304",
"Mumbai":"19.07283,72.88261",
"Pune":"18.51957,73.85535",
"Surat":"21.19594,72.83023"}
for c, o in cities.items():
lat = o.split(",")[0]
lon = o.split(",")[1]
How can I calculate all the distances between any 2 cities in the dictionary?
Thank you.
If user gives two city names as input, you can simply do:
def dist_two_cities(city1,city2):
lat1 = cities[city1].split(",")[0]
lon1 = cities[city1].split(",")[0]
lat2 = cities[city2].split(",")[0]
lon2 = cities[city2].split(",")[0]
return cor_dist_calculator(lat1, lat2, lon1, lon2)
And, if you want to calculate randomly for all - you can loop over.
You have already done most of the things. It is just a matter of taking the input from the user and formatting it as per your needs.
if __name__ == "__main__":
city1, city2 = input("Enter the name of the city seperated by comma\n").split(',')
lat1, long1 = cities.get(city1.strip()).split(',')
lat2, long2 = cities.get(city2.strip()).split(',')
cor_dist_calculator(radians(float(lat1)), radians(float(lat2)), radians(float(long1)), radians(float(long2)))
Code
from math import sin, cos, sqrt, atan2, radians
import json
def cor_dist_calculator(lat1, lat2, lon1, lon2):
R = 6373.0
dlon = lon2 - lon1
dlat = lat2 - lat1
a = sin(dlat / 2)**2 + cos(lat1) * cos(lat2) * sin(dlon / 2)**2
c = 2 * atan2(sqrt(a), sqrt(1 - a))
distance = R * c
return distance # Change to return result instead of printing
cities = {
"Ahmedabad":"23.02579,72.58727",
"Bengaluru":"12.97194,77.59369",
"Chennai":"13.08784,80.27847",
"Delhi":"28.65195,77.23149",
"Hyderabad":"17.38405,78.45636",
"Kanpur":"26.46523,80.34975",
"Kolkata":"22.56263,88.36304",
"Mumbai":"19.07283,72.88261",
"Pune":"18.51957,73.85535",
"Surat":"21.19594,72.83023"
}
result = { } # result cache
for c1, o1 in cities.items():
for c2, o2 in cities.items():
if c1 == c2: # Skip distance to itself
continue
if c1 not in result:
result[c1] = {}
if c2 not in result:
result[c2] = {}
if c2 in result[c1]: # Skip calculation if result exists
continue
lat1, lon1 = o1.split(",")
lat2, lon2 = o2.split(",")
lat1, lon1, lat2, lon2 = float(lat1), float(lon1), float(lat2), float(lon2)
dist = cor_dist_calculator(radians(lat1), radians(lat2), radians(lon1), radians(lon2))
result[c1][c2] = dist
result[c2][c1] = dist
# Use JSON to pretty print
print(json.dumps(result, sort_keys=True, indent=4))
Output
{
"Ahmedabad": {
"Bengaluru": 1236.9685147466164,
"Chennai": 1371.5560941922058,
"Delhi": 779.3993196898124,
"Hyderabad": 876.7339794841921,
"Kanpur": 872.2163865213793,
"Kolkata": 1617.7373028708505,
"Mumbai": 440.75405570398016,
"Pune": 518.2729673252524,
"Surat": 205.06784688939214
},
"Bengaluru": {
"Ahmedabad": 1236.9685147466164,
"Chennai": 291.2228040150677,
"Delhi": 1744.487772289504,
"Hyderabad": 499.41428330226853,
"Kanpur": 1528.1728332155533,
"Kolkata": 1560.4315624298629,
"Mumbai": 844.9020405056748,
"Pune": 735.3744543489997,
"Surat": 1045.3221688709566
},
"Chennai": {
"Ahmedabad": 1371.5560941922058,
"Bengaluru": 291.2228040150677,
"Delhi": 1759.6662314194639,
"Hyderabad": 516.3080888651748,
"Kanpur": 1487.983445250212,
"Kolkata": 1356.9170709394425,
"Mumbai": 1033.058314823502,
"Pune": 914.9401253270859,
"Surat": 1199.443950315355
},
"Delhi": {
"Ahmedabad": 779.3993196898124,
"Bengaluru": 1744.487772289504,
"Chennai": 1759.6662314194639,
"Hyderabad": 1259.5527686310922,
"Kanpur": 392.0259915147513,
"Kolkata": 1304.8787459771033,
"Mumbai": 1153.348591508457,
"Pune": 1178.1906584531494,
"Surat": 940.4321887894869
},
"Hyderabad": {
"Ahmedabad": 876.7339794841921,
"Bengaluru": 499.41428330226853,
"Chennai": 516.3080888651748,
"Delhi": 1259.5527686310922,
"Kanpur": 1028.7605594631257,
"Kolkata": 1184.4860919672817,
"Mumbai": 618.0416762200242,
"Pune": 502.9490477553323,
"Surat": 726.9427844409639
},
"Kanpur": {
"Ahmedabad": 872.2163865213793,
"Bengaluru": 1528.1728332155533,
"Chennai": 1487.983445250212,
"Delhi": 392.0259915147513,
"Hyderabad": 1028.7605594631257,
"Kolkata": 919.5167629722739,
"Mumbai": 1123.0549698313646,
"Pune": 1106.9736378339578,
"Surat": 963.370481325532
},
"Kolkata": {
"Ahmedabad": 1617.7373028708505,
"Bengaluru": 1560.4315624298629,
"Chennai": 1356.9170709394425,
"Delhi": 1304.8787459771033,
"Hyderabad": 1184.4860919672817,
"Kanpur": 919.5167629722739,
"Mumbai": 1654.6687139324506,
"Pune": 1575.6823437947044,
"Surat": 1609.718084142609
},
"Mumbai": {
"Ahmedabad": 440.75405570398016,
"Bengaluru": 844.9020405056748,
"Chennai": 1033.058314823502,
"Delhi": 1153.348591508457,
"Hyderabad": 618.0416762200242,
"Kanpur": 1123.0549698313646,
"Kolkata": 1654.6687139324506,
"Pune": 119.49195110246427,
"Surat": 236.21650702410025
},
"Pune": {
"Ahmedabad": 518.2729673252524,
"Bengaluru": 735.3744543489997,
"Chennai": 914.9401253270859,
"Delhi": 1178.1906584531494,
"Hyderabad": 502.9490477553323,
"Kanpur": 1106.9736378339578,
"Kolkata": 1575.6823437947044,
"Mumbai": 119.49195110246427,
"Surat": 316.4157942067634
},
"Surat": {
"Ahmedabad": 205.06784688939214,
"Bengaluru": 1045.3221688709566,
"Chennai": 1199.443950315355,
"Delhi": 940.4321887894869,
"Hyderabad": 726.9427844409639,
"Kanpur": 963.370481325532,
"Kolkata": 1609.718084142609,
"Mumbai": 236.21650702410025,
"Pune": 316.4157942067634
}
}
I'd suggest to add this line to the calculator just below the def:
lat1, lat2, lon1, lon2 = radians(lat1), radians(lat2), radians(lon1), radians(lon2)
So you can easily enter the coordinates in degrees.
Then, build a list with the combinations of two cities (to avoid calculating distance from city to itself or city1-city2 and city2-city1):
import itertools
comb_cities = list(itertools.combinations(cities.keys(), 2))
res = []
for city1, city2 in comb_cities:
distance = cor_dist_calculator(int(cities[city1][0]),int(cities[city1][1]), int(cities[city2][0]),int(cities[city2][1]) )
res.append((city1, city2, distance))
Now res contains:
[('Ahmedabad', 'Bengaluru', 157.22689337854425), ('Ahmedabad', 'Chennai', 248.52555085450666), ('Ahmedabad', 'Delhi', 675.9491465155114), ('Ahmedabad', 'Hyderabad', 675.9491465155114), ......
If you want the distance in both directions (which is the same:)) change itertools.combinations
to itertools.permutations
.
Using permutations
you can get the information back like this:
city1 = "Surat"
city2 = "Bengaluru"
print ([ cities for cities in res if cities[0] == city1 and cities[1] == city2])
The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.