Skip to main content

Find distance between two points

The haversine formula is an equation important in navigation, giving great-circle distances between two points on a sphere from their longitudes and latitudes 🌎

It is a special case of a more general formula in spherical trigonometry, the law of haversines, relating the sides and angles of spherical "triangles".

Task:
Implement a great-circle distance function, or use a library function, to show the great-circle distance between:

  • Wagle Estate Rd, Padwal Nagar, Thane West, Thane, Maharashtra 400604, which is:
   N 19.189354,   W 72.951225
  • Swami Vivekananda Rd, Thane West, Thane, Maharashtra 400602, which is:
   N 19.186333,   W 72.966961 


Distance:
This uses the ‘haversine’ formula to calculate the great-circle distance between two points – that is, the shortest distance over the earth’s surface – giving an ‘as-the-crow-flies’ distance between the points (ignoring any hills they fly over, of course!).
Haversine
formula:
a = sin²(Δφ/2) + cos φ1 ⋅ cos φ2 ⋅ sin²(Δλ/2)
c = 2 ⋅ atan2( √a, √(1−a) )
d = R ⋅ c
whereφ is latitude, λ is longitude, R is earth’s radius (mean radius = 6,371km);
note that angles need to be in radians to pass to trig functions!



Most of the examples below adopted Kaimbridge's recommended value of 6372.8 km for the earth radius. However, the derivation of this ellipsoidal quadratic mean radius is wrong (the averaging over azimuth is biased). When applying these examples in real applications, it is better to use the mean earth radius, 6371 km. This value is recommended by the International Union of Geodesy and Geophysics and it minimizes the RMS relative error between the great circle and geodesic distance.
package main.java.haversine;

public class Haversine {
    private static final int EARTH_RADIUS = 6371; // Approx Earth radius in KM
    public static double distance(double startLat, double startLong,
                                  double endLat, double endLong) {

        double dLatitudes  = Math.toRadians((endLat - startLat));
        double dLongitudes = Math.toRadians((endLong - startLong));

        startLat = Math.toRadians(startLat);
        endLat   = Math.toRadians(endLat);

        double a = haversine(dLatitudes) + Math.cos(startLat)
                * Math.cos(endLat) * haversine(dLongitudes);

        double c = 2 * Math.atan2(Math.sqrt(a), Math.sqrt(1 - a));

        return EARTH_RADIUS * c; // <-- d    }

    public static double haversine(double val) {
        return Math.pow(Math.sin(val / 2), 2);
    }

    public static void main(String[] args)
    {
        //example->1        double lat1 = 19.189354;
        double lon1 = 72.951225;
        double lat2 = 19.186333;
        double lon2 = 72.966961;
        System.out.println(distance(lat1, lon1, lat2, lon2) + " K.M.");

        //example->2        double lat11 = 51.5007;
        double lon12 = 0.1246;
        double lat22 = 40.6892;
        double lon22 = 74.0445;
        System.out.println(distance(lat11, lon12, lat22, lon22) + " K.M.");
    }
}
Output:
1.6863533312765095 K.M.
5574.840456848555 K.M.

The distance between New York (40.6892° N, 74.0445° W) is 5574.8 km. This is not the exact measurement because the formula assumes that the Earth is a perfect sphere when in fact it is an oblate spheroid.

Comments

Popular posts from this blog

Java Currency Formatter Solution

Given a  double-precision  number,  , denoting an amount of money, use the  NumberFormat  class'  getCurrencyInstance  method to convert   into the US, Indian, Chinese, and French currency formats. Then print the formatted values as follows: US: formattedPayment India: formattedPayment China: formattedPayment France: formattedPayment where   is   formatted according to the appropriate  Locale 's currency. Note:  India does not have a built-in Locale, so you must  construct one  where the language is  en  (i.e., English). Input Format A single double-precision number denoting  . Constraints Output Format On the first line, print  US: u  where   is   formatted for US currency.  On the second line, print  India: i  where   is   formatted for Indian currency.  On the third line...

Java Loops II print each element of our series as a single line of space-separated values.

We use the integers  ,  , and   to create the following series: You are given   queries in the form of  ,  , and  . For each query, print the series corresponding to the given  ,  , and   values as a single line of   space-separated integers. Input Format The first line contains an integer,  , denoting the number of queries.  Each line   of the   subsequent lines contains three space-separated integers describing the respective  ,  , and   values for that query. Constraints Output Format For each query, print the corresponding series on a new line. Each series must be printed in order as a single line of   space-separated integers. Sample Input 2 0 2 10 5 3 5 Sample Output 2 6 14 30 62 126 254 510 1022 2046 8 14 26 50 98 Explanation We have two queries: We use  ...

Java Static Initializer Block

Static initialization blocks are executed when the class is loaded, and you can initialize static variables in those blocks. It's time to test your knowledge of  Static initialization blocks . You can read about it  here. You are given a class  Solution  with a  main  method. Complete the given code so that it outputs the area of a parallelogram with breadth   and height  . You should read the variables from the standard input. If   or    , the output should be  "java.lang.Exception: Breadth and height must be positive"  without quotes. Input Format There are two lines of input. The first line contains  : the breadth of the parallelogram. The next line contains  : the height of the parallelogram. Constraints Output Format If both values are greater than zero, then the  main  method must output the area of the  parallelogram . Otherwise, pri...