distance calculation in python for google earth coordinates
Question: Hi I have a kml file called Placemark and 4 nodes (placemarks) that are
located in an area on Google Earth. Each placemark-node has a longitude and a
latitude.

    
    
    <?xml version="1.0" encoding="UTF-8"?>
    <kml xmlns="http://www.opengis.net/kml/2.2" xmlns:gx="http://www.google.com/kml/ext/2.2" xmlns:kml="http://www.opengis.net/kml/2.2" xmlns:atom="http://www.w3.org/2005/Atom">
    <Document>
        <name>placemarks.kml</name>
        <StyleMap id="m_ylw-pushpin">
            <Pair>
                <key>normal</key>
                <styleUrl>#s_ylw-pushpin</styleUrl>
            </Pair>
            <Pair>
                <key>highlight</key>
                <styleUrl>#s_ylw-pushpin_hl</styleUrl>
            </Pair>
        </StyleMap>
        <Style id="s_ylw-pushpin_hl">
            <IconStyle>
                <scale>1.3</scale>
                <Icon>
                    <href>http://maps.google.com/mapfiles/kml/pushpin/ylw-pushpin.png</href>
                </Icon>
                <hotSpot x="20" y="2" xunits="pixels" yunits="pixels"/>
            </IconStyle>
        </Style>
        <Style id="s_ylw-pushpin">
            <IconStyle>
                <scale>1.1</scale>
                <Icon>
                    <href>http://maps.google.com/mapfiles/kml/pushpin/ylw-pushpin.png</href>
                </Icon>
                <hotSpot x="20" y="2" xunits="pixels" yunits="pixels"/>
            </IconStyle>
        </Style>
        <Folder>
            <name>placemarks</name>
            <open>1</open>
            <Placemark>
                <name>node0</name>
                <LookAt>
                    <longitude>21.78832062146911</longitude>
                    <latitude>38.28791526390673</latitude>
                    <altitude>0</altitude>
                    <heading>0.001539813336055052</heading>
                    <tilt>44.99941206765101</tilt>
                    <range>990.2435222326291</range>
                    <gx:altitudeMode>relativeToSeaFloor</gx:altitudeMode>
                </LookAt>
                <styleUrl>#m_ylw-pushpin</styleUrl>
                <Point>
                    <coordinates>21.78400936610002,38.2874355527483,67.51641688336248</coordinates>
                </Point>
            </Placemark>
            <Placemark>
                <name>node1</name>
                <LookAt>
                    <longitude>21.78832062146911</longitude>
                    <latitude>38.28791526390673</latitude>
                    <altitude>0</altitude>
                    <heading>0.001539813336055052</heading>
                    <tilt>44.99941206765101</tilt>
                    <range>990.2435222326291</range>
                    <gx:altitudeMode>relativeToSeaFloor</gx:altitudeMode>
                </LookAt>
                <styleUrl>#m_ylw-pushpin</styleUrl>
                <Point>
                    <coordinates>21.78453228393861,38.28690995466475,67.51641688336248</coordinates>
                </Point>
            </Placemark>
            <Placemark>
                <name>node2</name>
                <LookAt>
                    <longitude>21.78832062146911</longitude>
                    <latitude>38.28791526390673</latitude>
                    <altitude>0</altitude>
                    <heading>0.001539813336055052</heading>
                    <tilt>44.99941206765101</tilt>
                    <range>990.2435222326291</range>
                    <gx:altitudeMode>relativeToSeaFloor</gx:altitudeMode>
                </LookAt>
                <styleUrl>#m_ylw-pushpin</styleUrl>
                <Point>
                    <coordinates>21.7848823502596,38.2869152766261,67.51641688336248</coordinates>
                </Point>
            </Placemark>
            <Placemark>
                <name>node3</name>
                <LookAt>
                    <longitude>21.78832062146911</longitude>
                    <latitude>38.28791526390673</latitude>
                    <altitude>0</altitude>
                    <heading>0.001539813336055052</heading>
                    <tilt>44.99941206765101</tilt>
                    <range>990.2435222326291</range>
                    <gx:altitudeMode>relativeToSeaFloor</gx:altitudeMode>
                </LookAt>
                <styleUrl>#m_ylw-pushpin</styleUrl>
                <Point>
                    <coordinates>21.78459887820567,38.28740826552452,67.51641688336248</coordinates>
                </Point>
            </Placemark>
        </Folder>
    </Document>
    </kml>
    

What I want is to calculate the distance between node0 and node2,3,4...
(keeping node0 constant in the distance function) and then, print the results.

By using the code below: (I need to modify it in order to have the output
below)

    
    
     # adapted from haversine.py <https://gist.github.com/rochacbruno/2883505>
        # see also <http://en.wikipedia.org/wiki/Haversine_formula>
        from math import atan2, cos, sin, sqrt, radians
    
        def calc_distance(origin, destination):
            """great-circle distance between two points on a sphere
               from their longitudes and latitudes"""
            lat1, lon1 = origin
            lat2, lon2 = destination
            radius = 6371 # km. earth
    
            dlat = radians(lat2-lat1)
            dlon = radians(lon2-lon1)
            a = (sin(dlat/2) * sin(dlat/2) + cos(radians(lat1)) * cos(radians(lat2)) *
                 sin(dlon/2) * sin(dlon/2))
            c = 2 * atan2(sqrt(a), sqrt(1-a))
            d = radius * c
    
            return d
    
        from xml.dom import minidom
    
        xmldoc = minidom.parse("placemarks.kml")
        kml = xmldoc.getElementsByTagName("kml")[0]
        document = kml.getElementsByTagName("Document")[0]
        placemarks = document.getElementsByTagName("Placemark")
    
        nodes = {}
        for placemark in placemarks:
            nodename = placemark.getElementsByTagName("name")[0].firstChild.data[:-1]
            coords = placemark.getElementsByTagName("coordinates")[0].firstChild.data
            lst1 = coords.split(",")
            longitude = float(lst1[0])
            latitude = float(lst1[1])
            nodes[nodename] = (latitude, longitude)
    

Ang get an output like:

    
    
    node1: (21.78453228393861, 38.28690995466475), distance from node0: 
    node2: (21.78488235025960, 38.28691527662610), distance from node0: 
    node3: (21.78459887820567, 38.28740826552452), distance from node0: 
    


Answer: In the code where you collect nodes extracted from the KML file, the names of
nodes, as you extract them from the XML, are always the same, so when you try
to store it in the dictionary `nodes` you get only one point in the end. Here
is a corrected script (only the last part, which needed to be be fixed), which
I think does what you require (please tell us if it's not the case and you
need something else):

    
    
    nodes = {}
    for placemark in placemarks:
        nodename = placemark.getElementsByTagName("name")[0].firstChild.data
        coords = placemark.getElementsByTagName("coordinates")[0].firstChild.data
        lst1 = coords.split(",")
        longitude = float(lst1[0])
        latitude = float(lst1[1])
        nodes[nodename] = (latitude, longitude)
    
    for n in nodes:
        if n == 'node0':
            continue
        print n, nodes[n], 'distance from node0:', calc_distance(nodes['node0'], nodes[n])
    

Here is the output:

    
    
    node1 (38.28690995466475, 21.78453228393861) distance from node0: 0.074152874049
    node3 (38.28740826552452, 21.78459887820567) distance from node0: 0.0515409901388
    node2 (38.2869152766261, 21.7848823502596) distance from node0: 0.0956671636024
    

