A-M baby
This commit is contained in:
parent
764da6cbbb
commit
db842d013d
19005 changed files with 197040 additions and 7 deletions
25
Task/Haversine-formula/0DESCRIPTION
Normal file
25
Task/Haversine-formula/0DESCRIPTION
Normal file
|
|
@ -0,0 +1,25 @@
|
|||
{{Wikipedia}}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 Nashville International Airport (BNA) in Nashville, TN, USA: N 36°7.2', W 86°40.2' (36.12, -86.67) and Los Angeles International Airport (LAX) in Los Angeles, CA, USA: N 33°56.4', W 118°24.0' (33.94, -118.40).
|
||||
|
||||
<pre>
|
||||
User Kaimbridge clarified on the Talk page:
|
||||
|
||||
-- 6371.0 km is the authalic radius based on/extracted from surface area;
|
||||
-- 6372.8 km is an approximation of the radius of the average circumference
|
||||
(i.e., the average great-elliptic or great-circle radius), where the
|
||||
boundaries are the meridian (6367.45 km) and the equator (6378.14 km).
|
||||
|
||||
Using either of these values results, of course, in differing distances:
|
||||
|
||||
6371.0 km -> 2886.44444283798329974715782394574671655 km;
|
||||
6372.8 km -> 2887.25995060711033944886005029688505340 km;
|
||||
(results extended for accuracy check: Given that the radii are only
|
||||
approximations anyways, .01' ≈ 1.0621333 km and .001" ≈ .00177 km,
|
||||
practical precision required is certainly no greater than about
|
||||
.0000001——i.e., .1 mm!)
|
||||
|
||||
As distances are segments of great circles/circumferences, it is
|
||||
recommended that the latter value (r = 6372.8 km) be used (which
|
||||
most of the given solutions have already adopted, anyways).
|
||||
</pre>
|
||||
22
Task/Haversine-formula/ALGOL-68/haversine-formula.alg
Normal file
22
Task/Haversine-formula/ALGOL-68/haversine-formula.alg
Normal file
|
|
@ -0,0 +1,22 @@
|
|||
#!/usr/local/bin/a68g --script #
|
||||
|
||||
REAL r = 20 000/pi + 6.6 # km #,
|
||||
to rad = pi/180;
|
||||
|
||||
PROC dist = (REAL th1 deg, ph1 deg, th2 deg, ph2 deg)REAL:
|
||||
(
|
||||
REAL ph1 = (ph1 deg - ph2 deg) * to rad,
|
||||
th1 = th1 deg * to rad, th2 = th2 deg * to rad,
|
||||
|
||||
dz = sin(th1) - sin(th2),
|
||||
dx = cos(ph1) * cos(th1) - cos(th2),
|
||||
dy = sin(ph1) * cos(th1);
|
||||
arc sin(sqrt(dx * dx + dy * dy + dz * dz) / 2) * 2 * r
|
||||
);
|
||||
|
||||
main:
|
||||
(
|
||||
REAL d = dist(36.12, -86.67, 33.94, -118.4);
|
||||
# Americans don't know kilometers #
|
||||
printf(($"dist: "g(0,1)" km ("g(0,1)" mi.)"l$, d, d / 1.609344))
|
||||
)
|
||||
18
Task/Haversine-formula/AWK/haversine-formula.awk
Normal file
18
Task/Haversine-formula/AWK/haversine-formula.awk
Normal file
|
|
@ -0,0 +1,18 @@
|
|||
# syntax: GAWK -f HAVERSINE_FORMULA.AWK
|
||||
# converted from Python
|
||||
BEGIN {
|
||||
distance(36.12,-86.67,33.94,-118.40) # BNA to LAX
|
||||
exit(0)
|
||||
}
|
||||
function distance(lat1,lon1,lat2,lon2, a,c,dlat,dlon) {
|
||||
dlat = radians(lat2-lat1)
|
||||
dlon = radians(lon2-lon1)
|
||||
lat1 = radians(lat1)
|
||||
lat2 = radians(lat2)
|
||||
a = (sin(dlat/2))^2 + cos(lat1) * cos(lat2) * (sin(dlon/2))^2
|
||||
c = 2 * atan2(sqrt(a),sqrt(1-a))
|
||||
printf("distance: %.4f km\n",6372.8 * c)
|
||||
}
|
||||
function radians(degree) { # degrees to radians
|
||||
return degree * (3.1415926 / 180.)
|
||||
}
|
||||
31
Task/Haversine-formula/Ada/haversine-formula.ada
Normal file
31
Task/Haversine-formula/Ada/haversine-formula.ada
Normal file
|
|
@ -0,0 +1,31 @@
|
|||
with Ada.Text_IO; use Ada.Text_IO;
|
||||
with Ada.Long_Float_Text_IO; use Ada.Long_Float_Text_IO;
|
||||
with Ada.Numerics.Generic_Elementary_Functions;
|
||||
|
||||
procedure Haversine_Formula is
|
||||
|
||||
package Math is new Ada.Numerics.Generic_Elementary_Functions (Long_Float); use Math;
|
||||
|
||||
-- Compute great circle distance, given latitude and longitude of two points, in radians
|
||||
function Great_Circle_Distance (lat1, long1, lat2, long2 : Long_Float) return Long_Float is
|
||||
Earth_Radius : constant := 6371.0; -- in kilometers
|
||||
a : Long_Float := Sin (0.5 * (lat2 - lat1));
|
||||
b : Long_Float := Sin (0.5 * (long2 - long1));
|
||||
begin
|
||||
return 2.0 * Earth_Radius * ArcSin (Sqrt (a * a + Cos (lat1) * Cos (lat2) * b * b));
|
||||
end Great_Circle_Distance;
|
||||
|
||||
-- convert degrees, minutes and seconds to radians
|
||||
function DMS_To_Radians (Deg, Min, Sec : Long_Float := 0.0) return Long_Float is
|
||||
Pi_Over_180 : constant := 0.017453_292519_943295_769236_907684_886127;
|
||||
begin
|
||||
return (Deg + Min/60.0 + Sec/3600.0) * Pi_Over_180;
|
||||
end DMS_To_Radians;
|
||||
|
||||
begin
|
||||
Put_Line("Distance in kilometers between BNA and LAX");
|
||||
Put (Great_Circle_Distance (
|
||||
DMS_To_Radians (36.0, 7.2), DMS_To_Radians (86.0, 40.2), -- Nashville International Airport (BNA)
|
||||
DMS_To_Radians (33.0, 56.4), DMS_To_Radians (118.0, 24.0)), -- Los Angeles International Airport (LAX)
|
||||
Aft=>3, Exp=>0);
|
||||
end Haversine_Formula;
|
||||
9
Task/Haversine-formula/BBC-BASIC/haversine-formula.bbc
Normal file
9
Task/Haversine-formula/BBC-BASIC/haversine-formula.bbc
Normal file
|
|
@ -0,0 +1,9 @@
|
|||
PRINT "Distance = " ; FNhaversine(36.12, -86.67, 33.94, -118.4) " km"
|
||||
END
|
||||
|
||||
DEF FNhaversine(n1, e1, n2, e2)
|
||||
LOCAL d() : DIM d(2)
|
||||
d() = COSRAD(e1-e2) * COSRAD(n1) - COSRAD(n2), \
|
||||
\ SINRAD(e1-e2) * COSRAD(n1), \
|
||||
\ SINRAD(n1) - SINRAD(n2)
|
||||
= ASN(MOD(d()) / 2) * 6372.8 * 2
|
||||
26
Task/Haversine-formula/C/haversine-formula.c
Normal file
26
Task/Haversine-formula/C/haversine-formula.c
Normal file
|
|
@ -0,0 +1,26 @@
|
|||
#include <stdio.h>
|
||||
#include <stdlib.h>
|
||||
#include <math.h>
|
||||
|
||||
#define R 6371
|
||||
#define TO_RAD (3.1415926536 / 180)
|
||||
double dist(double th1, double ph1, double th2, double ph2)
|
||||
{
|
||||
double dx, dy, dz;
|
||||
ph1 -= ph2;
|
||||
ph1 *= TO_RAD, th1 *= TO_RAD, th2 *= TO_RAD;
|
||||
|
||||
dz = sin(th1) - sin(th2);
|
||||
dx = cos(ph1) * cos(th1) - cos(th2);
|
||||
dy = sin(ph1) * cos(th1);
|
||||
return asin(sqrt(dx * dx + dy * dy + dz * dz) / 2) * 2 * R;
|
||||
}
|
||||
|
||||
int main()
|
||||
{
|
||||
double d = dist(36.12, -86.67, 33.94, -118.4);
|
||||
/* Americans don't know kilometers */
|
||||
printf("dist: %.1f km (%.1f mi.)\n", d, d / 1.609344);
|
||||
|
||||
return 0;
|
||||
}
|
||||
21
Task/Haversine-formula/Common-Lisp/haversine-formula.lisp
Normal file
21
Task/Haversine-formula/Common-Lisp/haversine-formula.lisp
Normal file
|
|
@ -0,0 +1,21 @@
|
|||
(defparameter *earth-radius* 6372.8)
|
||||
|
||||
(defparameter *rad-conv* (/ pi 180))
|
||||
|
||||
(defun deg->rad (x)
|
||||
(* x *rad-conv*))
|
||||
|
||||
(defun haversine (x)
|
||||
(expt (sin (/ x 2)) 2))
|
||||
|
||||
(defun dist-rad (lat1 lng1 lat2 lng2)
|
||||
(let* ((hlat (haversine (- lat2 lat1)))
|
||||
(hlng (haversine (- lng2 lng1)))
|
||||
(root (sqrt (+ hlat (* (cos lat1) (cos lat2) hlng)))))
|
||||
(* 2 *earth-radius* (asin root))))
|
||||
|
||||
(defun dist-deg (lat1 lng1 lat2 lng2)
|
||||
(dist-rad (deg->rad lat1)
|
||||
(deg->rad lng1)
|
||||
(deg->rad lat2)
|
||||
(deg->rad lng2)))
|
||||
24
Task/Haversine-formula/D/haversine-formula.d
Normal file
24
Task/Haversine-formula/D/haversine-formula.d
Normal file
|
|
@ -0,0 +1,24 @@
|
|||
import std.stdio, std.math;
|
||||
|
||||
real haversineDistance(in real dth1, in real dph1,
|
||||
in real dth2, in real dph2) pure nothrow {
|
||||
|
||||
enum real R = 6371;
|
||||
enum real TO_RAD = PI / 180;
|
||||
|
||||
alias imr = immutable(real);
|
||||
imr ph1d = dph1 - dph2;
|
||||
imr ph1 = ph1d * TO_RAD;
|
||||
imr th1 = dth1 * TO_RAD;
|
||||
imr th2 = dth2 * TO_RAD;
|
||||
|
||||
imr dz = sin(th1) - sin(th2);
|
||||
imr dx = cos(ph1) * cos(th1) - cos(th2);
|
||||
imr dy = sin(ph1) * cos(th1);
|
||||
return asin(sqrt(dx ^^ 2 + dy ^^ 2 + dz ^^ 2) / 2) * 2 * R;
|
||||
}
|
||||
|
||||
void main() {
|
||||
writefln("Haversine distance: %.1f km",
|
||||
haversineDistance(36.12, -86.67, 33.94, -118.4));
|
||||
}
|
||||
11
Task/Haversine-formula/Factor/haversine-formula-1.factor
Normal file
11
Task/Haversine-formula/Factor/haversine-formula-1.factor
Normal file
|
|
@ -0,0 +1,11 @@
|
|||
USING: arrays kernel math math.constants math.functions math.vectors sequences ;
|
||||
|
||||
: haversin ( x -- y ) cos 1 swap - 2 / ;
|
||||
: haversininv ( y -- x ) 2 * 1 swap - acos ;
|
||||
: haversineDist ( as bs -- d )
|
||||
[ [ 180 / pi * ] map ] bi@
|
||||
[ [ swap - haversin ] 2map ]
|
||||
[ [ first cos ] bi@ * 1 swap 2array ]
|
||||
2bi
|
||||
v.
|
||||
haversininv R_earth * ;
|
||||
2
Task/Haversine-formula/Factor/haversine-formula-2.factor
Normal file
2
Task/Haversine-formula/Factor/haversine-formula-2.factor
Normal file
|
|
@ -0,0 +1,2 @@
|
|||
( scratchpad ) { 36.12 -86.67 } { 33.94 -118.4 } haversineDist .
|
||||
2887.259950607113
|
||||
15
Task/Haversine-formula/Forth/haversine-formula.fth
Normal file
15
Task/Haversine-formula/Forth/haversine-formula.fth
Normal file
|
|
@ -0,0 +1,15 @@
|
|||
: s>f s>d d>f ;
|
||||
: deg>rad 174532925199433e-16 f* ;
|
||||
: difference f- deg>rad 2 s>f f/ fsin fdup f* ;
|
||||
|
||||
: haversine ( lat1 lon1 lat2 lon2 -- haversine)
|
||||
frot difference ( lat1 lat2 dLon^2)
|
||||
frot frot fover fover ( dLon^2 lat1 lat2 lat1 lat2)
|
||||
fswap difference ( dLon^2 lat1 lat2 dLat^2)
|
||||
fswap deg>rad fcos ( dLon^2 lat1 dLat^2 lat2)
|
||||
frot deg>rad fcos f* ( dLon^2 dLat2 lat1*lat2)
|
||||
frot f* f+ ( lat1*lat2*dLon^2+dLat^2)
|
||||
fsqrt fasin 127456 s>f f* 10 s>f f/ ( haversine)
|
||||
;
|
||||
|
||||
36.12e -86.67e 33.94e -118.40e haversine cr f.
|
||||
34
Task/Haversine-formula/Fortran/haversine-formula.f
Normal file
34
Task/Haversine-formula/Fortran/haversine-formula.f
Normal file
|
|
@ -0,0 +1,34 @@
|
|||
program example
|
||||
implicit none
|
||||
real :: d
|
||||
|
||||
d = haversine(36.12,-86.67,33.94,-118.40) ! BNA to LAX
|
||||
print '(A,F9.4,A)', 'distance: ',d,' km' ! distance: 2887.2600 km
|
||||
|
||||
contains
|
||||
|
||||
function to_radian(degree) result(rad)
|
||||
! degrees to radians
|
||||
real,intent(in) :: degree
|
||||
real :: rad,pi
|
||||
|
||||
pi = 4*atan(1.0) ! exploit intrinsic atan to generate pi
|
||||
rad = degree*pi/180
|
||||
end function to_radian
|
||||
|
||||
function haversine(deglat1,deglon1,deglat2,deglon2) result (dist)
|
||||
! great circle distance -- adapted from Matlab
|
||||
real,intent(in) :: deglat1,deglon1,deglat2,deglon2
|
||||
real :: a,c,dist,dlat,dlon,lat1,lat2
|
||||
real,parameter :: radius = 6372.8
|
||||
|
||||
dlat = to_radian(deglat2-deglat1)
|
||||
dlon = to_radian(deglon2-deglon1)
|
||||
lat1 = to_radian(deglat1)
|
||||
lat2 = to_radian(deglat2)
|
||||
a = (sin(dlat/2))**2 + cos(lat1)*cos(lat2)*(sin(dlon/2))**2
|
||||
c = 2*atan2(sqrt(a),sqrt(1-a))
|
||||
dist = radius*c
|
||||
end function haversine
|
||||
|
||||
end program example
|
||||
6
Task/Haversine-formula/Frink/haversine-formula-1.frink
Normal file
6
Task/Haversine-formula/Frink/haversine-formula-1.frink
Normal file
|
|
@ -0,0 +1,6 @@
|
|||
haversine[theta] := (1-cos[theta])/2
|
||||
|
||||
dist[lat1, long1, lat2, long2] := 2 earthradius arcsin[sqrt[haversine[lat2-lat1] + cos[lat1] cos[lat2] haversine[long2-long1]]]
|
||||
|
||||
d = dist[36.12 deg, -86.67 deg, 33.94 deg, -118.40 deg]
|
||||
println[d-> "km"]
|
||||
4
Task/Haversine-formula/Frink/haversine-formula-2.frink
Normal file
4
Task/Haversine-formula/Frink/haversine-formula-2.frink
Normal file
|
|
@ -0,0 +1,4 @@
|
|||
use navigation.frink
|
||||
|
||||
d = earthDistance[36.12 deg North, 86.67 deg West, 33.94 deg North, 118.40 deg West]
|
||||
println[d-> "km"]
|
||||
30
Task/Haversine-formula/Go/haversine-formula.go
Normal file
30
Task/Haversine-formula/Go/haversine-formula.go
Normal file
|
|
@ -0,0 +1,30 @@
|
|||
package main
|
||||
|
||||
import (
|
||||
"fmt"
|
||||
"math"
|
||||
)
|
||||
|
||||
func haversine(θ float64) float64 {
|
||||
return .5 * (1 - math.Cos(θ))
|
||||
}
|
||||
|
||||
type pos struct {
|
||||
φ float64 // latitude, radians
|
||||
ψ float64 // longitude, radians
|
||||
}
|
||||
|
||||
func degPos(lat, lon float64) pos {
|
||||
return pos{lat * math.Pi / 180, lon * math.Pi / 180}
|
||||
}
|
||||
|
||||
const rEarth = 6372.8 // km
|
||||
|
||||
func hsDist(p1, p2 pos) float64 {
|
||||
return 2 * rEarth * math.Asin(math.Sqrt(haversine(p2.φ-p1.φ)+
|
||||
math.Cos(p1.φ)*math.Cos(p2.φ)*haversine(p2.ψ-p1.ψ)))
|
||||
}
|
||||
|
||||
func main() {
|
||||
fmt.Println(hsDist(degPos(36.12, -86.67), degPos(33.94, -118.40)))
|
||||
}
|
||||
16
Task/Haversine-formula/Groovy/haversine-formula.groovy
Normal file
16
Task/Haversine-formula/Groovy/haversine-formula.groovy
Normal file
|
|
@ -0,0 +1,16 @@
|
|||
def haversine(lat1, lon1, lat2, lon2) {
|
||||
def R = 6372.8
|
||||
// In kilometers
|
||||
def dLat = Math.toRadians(lat2 - lat1)
|
||||
def dLon = Math.toRadians(lon2 - lon1)
|
||||
lat1 = Math.toRadians(lat1)
|
||||
lat2 = Math.toRadians(lat2)
|
||||
|
||||
def a = Math.sin(dLat / 2) * Math.sin(dLat / 2) + Math.sin(dLon / 2) * Math.sin(dLon / 2) * Math.cos(lat1) * Math.cos(lat2)
|
||||
def c = 2 * Math.asin(Math.sqrt(a))
|
||||
R * c
|
||||
}
|
||||
|
||||
haversine(36.12, -86.67, 33.94, -118.40)
|
||||
|
||||
> 2887.25995060711
|
||||
28
Task/Haversine-formula/Haskell/haversine-formula.hs
Normal file
28
Task/Haversine-formula/Haskell/haversine-formula.hs
Normal file
|
|
@ -0,0 +1,28 @@
|
|||
import Text.Printf
|
||||
|
||||
-- The haversine of an angle.
|
||||
hsin t = let u = sin (t/2) in u*u
|
||||
|
||||
-- The distance between two points, given by latitude and longtitude, on a
|
||||
-- circle. The points are specified in radians.
|
||||
distRad radius (lat1, lng1) (lat2, lng2) =
|
||||
let hlat = hsin (lat2 - lat1)
|
||||
hlng = hsin (lng2 - lng1)
|
||||
root = sqrt (hlat + cos lat1 * cos lat2 * hlng)
|
||||
in 2 * radius * asin (min 1.0 root)
|
||||
|
||||
-- The distance between two points, given by latitude and longtitude, on a
|
||||
-- circle. The points are specified in degrees.
|
||||
distDeg radius p1 p2 = distRad radius (deg2rad p1) (deg2rad p2)
|
||||
where deg2rad (t, u) = (d2r t, d2r u)
|
||||
d2r t = t * pi / 180
|
||||
|
||||
-- The approximate distance, in kilometers, between two points on Earth. The
|
||||
-- latitude and longtitude are assumed to be in degrees.
|
||||
earthDist = distDeg 6372.8
|
||||
|
||||
main = do
|
||||
let bna = (36.12, -86.67)
|
||||
lax = (33.94, -118.40)
|
||||
dst = earthDist bna lax :: Double
|
||||
printf "The distance between BNA and LAX is about %0.f km.\n" dst
|
||||
15
Task/Haversine-formula/Icon/haversine-formula.icon
Normal file
15
Task/Haversine-formula/Icon/haversine-formula.icon
Normal file
|
|
@ -0,0 +1,15 @@
|
|||
link printf
|
||||
|
||||
procedure main() #: Haversine formula
|
||||
printf("BNA to LAX is %d km (%d miles)\n",
|
||||
d := gcdistance([36.12, -86.67],[33.94, -118.40]),d*3280/5280) # with cute km2mi conversion
|
||||
end
|
||||
|
||||
procedure gcdistance(a,b)
|
||||
a[2] -:= b[2]
|
||||
every (x := a|b)[i := 1 to 2] := dtor(x[i])
|
||||
dz := sin(a[1]) - sin(b[1])
|
||||
dx := cos(a[2]) * cos(a[1]) - cos(b[1])
|
||||
dy := sin(a[2]) * cos(a[1])
|
||||
return asin(sqrt(dx * dx + dy * dy + dz * dz) / 2) * 2 * 6371
|
||||
end
|
||||
4
Task/Haversine-formula/J/haversine-formula-1.j
Normal file
4
Task/Haversine-formula/J/haversine-formula-1.j
Normal file
|
|
@ -0,0 +1,4 @@
|
|||
require 'trig'
|
||||
haversin=: 0.5 * 1 - cos
|
||||
Rearth=: 6372.8
|
||||
haversineDist=: Rearth * haversin^:_1@((1 , *&(cos@{.)) +/ .* [: haversin -)&rfd
|
||||
2
Task/Haversine-formula/J/haversine-formula-2.j
Normal file
2
Task/Haversine-formula/J/haversine-formula-2.j
Normal file
|
|
@ -0,0 +1,2 @@
|
|||
36.12 _86.67 haversineDist 33.94 _118.4
|
||||
2887.26
|
||||
16
Task/Haversine-formula/Java/haversine-formula.java
Normal file
16
Task/Haversine-formula/Java/haversine-formula.java
Normal file
|
|
@ -0,0 +1,16 @@
|
|||
public class Haversine {
|
||||
public static final double R = 6372.8; // In kilometers
|
||||
public static double haversine(double lat1, double lon1, double lat2, double lon2) {
|
||||
double dLat = Math.toRadians(lat2 - lat1);
|
||||
double dLon = Math.toRadians(lon2 - lon1);
|
||||
lat1 = Math.toRadians(lat1);
|
||||
lat2 = Math.toRadians(lat2);
|
||||
|
||||
double a = Math.sin(dLat / 2) * Math.sin(dLat / 2) + Math.sin(dLon / 2) * Math.sin(dLon / 2) * Math.cos(lat1) * Math.cos(lat2);
|
||||
double c = 2 * Math.asin(Math.sqrt(a));
|
||||
return R * c;
|
||||
}
|
||||
public static void main(String[] args) {
|
||||
System.out.println(haversine(36.12, -86.67, 33.94, -118.40));
|
||||
}
|
||||
}
|
||||
5
Task/Haversine-formula/Julia/haversine-formula.julia
Normal file
5
Task/Haversine-formula/Julia/haversine-formula.julia
Normal file
|
|
@ -0,0 +1,5 @@
|
|||
julia> haversine(lat1,lon1,lat2,lon2) = 2 * 6372.8 * asin(sqrt(sind((lat2-lat1)/2)^2 + cosd(lat1) * cosd(lat2) * sind((lon2 - lon1)/2)^2))
|
||||
# method added to generic function haversine
|
||||
|
||||
julia> haversine(36.12,-86.67,33.94,-118.4)
|
||||
2887.2599506071106
|
||||
|
|
@ -0,0 +1,13 @@
|
|||
print "Haversine distance: "; using( "####.###########", havDist( 36.12, -86.67, 33.94, -118.4)); " km."
|
||||
end
|
||||
function havDist( th1, ph1, th2, ph2)
|
||||
degtorad = acs(-1)/180
|
||||
diameter = 2 * 6372.8
|
||||
LgD = degtorad * (ph1 - ph2)
|
||||
th1 = degtorad * th1
|
||||
th2 = degtorad * th2
|
||||
dz = sin( th1) - sin( th2)
|
||||
dx = cos( LgD) * cos( th1) - cos( th2)
|
||||
dy = sin( LgD) * cos( th1)
|
||||
havDist = asn( ( dx^2 +dy^2 +dz^2)^0.5 /2) *diameter
|
||||
end function
|
||||
17
Task/Haversine-formula/MATLAB/haversine-formula.m
Normal file
17
Task/Haversine-formula/MATLAB/haversine-formula.m
Normal file
|
|
@ -0,0 +1,17 @@
|
|||
function rad = radians(degree)
|
||||
% degrees to radians
|
||||
rad = degree * pi / 180;
|
||||
end;
|
||||
|
||||
function [a,c,dlat,dlon]=haversine(lat1,lon1,lat2,lon2)
|
||||
% HAVERSINE_FORMULA.AWK - converted from AWK
|
||||
dlat = radians(lat2-lat1);
|
||||
dlon = radians(lon2-lon1);
|
||||
lat1 = radians(lat1);
|
||||
lat2 = radians(lat2);
|
||||
a = (sin(dlat/2))^2 + cos(lat1) * cos(lat2) * (sin(dlon/2))^2;
|
||||
c = 2 * atan2(sqrt(a),sqrt(1-a));
|
||||
printf("distance: %.4f km\n",6372.8 * c);
|
||||
end
|
||||
|
||||
[a,c,dlat,dlon] = haversine(36.12,-86.67,33.94,-118.40); % BNA to LAX
|
||||
|
|
@ -0,0 +1,4 @@
|
|||
distance[{theta1_, phi1_}, {theta2_, phi2_}] :=
|
||||
2*6378.14 ArcSin@
|
||||
Sqrt[Haversine[(theta2 - theta1) Degree] +
|
||||
Cos[theta1*Degree] Cos[theta2*Degree] Haversine[(phi2 - phi1) Degree]]
|
||||
12
Task/Haversine-formula/Maxima/haversine-formula.maxima
Normal file
12
Task/Haversine-formula/Maxima/haversine-formula.maxima
Normal file
|
|
@ -0,0 +1,12 @@
|
|||
dms(d, m, s) := (d + m/60 + s/3600)*%pi/180$
|
||||
|
||||
great_circle_distance(lat1, long1, lat2, long2) :=
|
||||
12742*asin(sqrt(sin((lat2 - lat1)/2)^2 + cos(lat1)*cos(lat2)*sin((long2 - long1)/2)^2))$
|
||||
|
||||
/* Coordinates are found here:
|
||||
http://www.airport-data.com/airport/BNA/
|
||||
http://www.airport-data.com/airport/LAX/ */
|
||||
|
||||
great_circle_distance(dms( 36, 7, 28.10), -dms( 86, 40, 41.50),
|
||||
dms( 33, 56, 32.98), -dms(118, 24, 29.05)), numer;
|
||||
/* 2886.326609413624 */
|
||||
21
Task/Haversine-formula/PHP/haversine-formula-1.php
Normal file
21
Task/Haversine-formula/PHP/haversine-formula-1.php
Normal file
|
|
@ -0,0 +1,21 @@
|
|||
class POI {
|
||||
private $latitude;
|
||||
private $longitude;
|
||||
public function __construct($latitude, $longitude) {
|
||||
$this->latitude = deg2rad($latitude);
|
||||
$this->longitude = deg2rad($longitude);
|
||||
}
|
||||
public function getLatitude() return $this->latitude;
|
||||
public function getLongitude() return $this->longitude;
|
||||
public function getDistanceInMetersTo(POI $other) {
|
||||
$radiusOfEarth = 6371000;// Earth's radius in meters.
|
||||
$diffLatitude = $other->getLatitude() - $this->latitude;
|
||||
$diffLongitude = $other->getLongitude() - $this->longitude;
|
||||
$a = sin($diffLatitude / 2) * sin($diffLatitude / 2) +
|
||||
cos($this->latitude) * cos($other->getLatitude()) *
|
||||
sin($diffLongitude / 2) * sin($diffLongitude / 2);
|
||||
$c = 2 * asin(sqrt($a));
|
||||
$distance = $radiusOfEarth * $c;
|
||||
return $distance;
|
||||
}
|
||||
}
|
||||
3
Task/Haversine-formula/PHP/haversine-formula-2.php
Normal file
3
Task/Haversine-formula/PHP/haversine-formula-2.php
Normal file
|
|
@ -0,0 +1,3 @@
|
|||
$user = new POI($_GET["latitude"], $_GET["longitude"]);
|
||||
$poi = new POI(19,69276, -98,84350); // Piramide del Sol, Mexico
|
||||
echo $user->getDistanceInMetersTo($poi);
|
||||
17
Task/Haversine-formula/PicoLisp/haversine-formula-1.l
Normal file
17
Task/Haversine-formula/PicoLisp/haversine-formula-1.l
Normal file
|
|
@ -0,0 +1,17 @@
|
|||
(scl 12)
|
||||
(load "@lib/math.l")
|
||||
|
||||
(de haversine (Th1 Ph1 Th2 Ph2)
|
||||
(setq
|
||||
Ph1 (*/ (- Ph1 Ph2) pi 180.0)
|
||||
Th1 (*/ Th1 pi 180.0)
|
||||
Th2 (*/ Th2 pi 180.0) )
|
||||
(let
|
||||
(DX (- (*/ (cos Ph1) (cos Th1) 1.0) (cos Th2))
|
||||
DY (*/ (sin Ph1) (cos Th1) 1.0)
|
||||
DZ (- (sin Th1) (sin Th2)) )
|
||||
(* `(* 2 6371)
|
||||
(asin
|
||||
(/
|
||||
(sqrt (+ (* DX DX) (* DY DY) (* DZ DZ)))
|
||||
2 ) ) ) ) )
|
||||
4
Task/Haversine-formula/PicoLisp/haversine-formula-2.l
Normal file
4
Task/Haversine-formula/PicoLisp/haversine-formula-2.l
Normal file
|
|
@ -0,0 +1,4 @@
|
|||
(prinl
|
||||
"Haversine distance: "
|
||||
(round (haversine 36.12 -86.67 33.94 -118.4))
|
||||
" km" )
|
||||
16
Task/Haversine-formula/Python/haversine-formula.py
Normal file
16
Task/Haversine-formula/Python/haversine-formula.py
Normal file
|
|
@ -0,0 +1,16 @@
|
|||
>>> import math
|
||||
>>> def haversine(lat1, lon1, lat2, lon2):
|
||||
R = 6372.8
|
||||
# In kilometers
|
||||
dLat = math.radians(lat2 - lat1)
|
||||
dLon = math.radians(lon2 - lon1)
|
||||
lat1 = math.radians(lat1)
|
||||
lat2 = math.radians(lat2)
|
||||
|
||||
a = math.sin(dLat / 2) * math.sin(dLat / 2) + math.sin(dLon / 2) * math.sin(dLon / 2) * math.cos(lat1) * math.cos(lat2)
|
||||
c = 2 * math.asin(math.sqrt(a))
|
||||
return R * c
|
||||
|
||||
>>> haversine(36.12, -86.67, 33.94, -118.40)
|
||||
2887.2599506071106
|
||||
>>>
|
||||
20
Task/Haversine-formula/R/haversine-formula.r
Normal file
20
Task/Haversine-formula/R/haversine-formula.r
Normal file
|
|
@ -0,0 +1,20 @@
|
|||
dms_to_rad <- function(d, m, s) (d + m / 60 + s / 3600) * pi / 180
|
||||
|
||||
# Volumetric mean radius is 6371 km, see http://nssdc.gsfc.nasa.gov/planetary/factsheet/earthfact.html
|
||||
# The diameter is thus 12742 km
|
||||
|
||||
great_circle_distance <- function(lat1, long1, lat2, long2) {
|
||||
a <- sin(0.5 * (lat2 - lat1))
|
||||
b <- sin(0.5 * (long2 - long1))
|
||||
12742 * asin(sqrt(a * a + cos(lat1) * cos(lat2) * b * b))
|
||||
}
|
||||
|
||||
# Coordinates are found here:
|
||||
# http://www.airport-data.com/airport/BNA/
|
||||
# http://www.airport-data.com/airport/LAX/
|
||||
|
||||
great_circle_distance(
|
||||
dms_to_rad(36, 7, 28.10), dms_to_rad( 86, 40, 41.50), # Nashville International Airport (BNA)
|
||||
dms_to_rad(33, 56, 32.98), dms_to_rad(118, 24, 29.05)) # Los Angeles International Airport (LAX)
|
||||
|
||||
# Output: 2886.327
|
||||
89
Task/Haversine-formula/REXX/haversine-formula.rexx
Normal file
89
Task/Haversine-formula/REXX/haversine-formula.rexx
Normal file
|
|
@ -0,0 +1,89 @@
|
|||
/*REXX pgm calculates distance between Nashville & Los Angles airports. */
|
||||
say " Nashville: north 36º 7.2', west 86º 40.2' = 36.12º, -86.67º"
|
||||
say "Los Angles: north 33º 56.4', west 118º 24.0' = 33.94º, -118.40º"
|
||||
say
|
||||
$.= /*set defaults for subroutines. */
|
||||
dist=surfaceDistance(36.12, -86.67, 33.94, -118.4)
|
||||
kdist=format(dist/1 ,,2) /*show 2 digs past decimal point.*/
|
||||
mdist=format(dist/1.609344,,2) /* " " " " " " */
|
||||
ndist=format(mdist*5280/6076.1,,2) /* " " " " " " */
|
||||
say ' distance between= ' kdist " kilometers,"
|
||||
say ' or ' mdist " statute miles,"
|
||||
say ' or ' ndist " nautical or air miles."
|
||||
exit /*stick a fork in it, we're done.*/
|
||||
/*──────────────────────────────────SURFACEDISTANCE subroutine──────────*/
|
||||
surfaceDistance: arg th1,ph1,th2,ph2 /*use haversine formula for dist.*/
|
||||
numeric digits digits()*2 /*double the number of digits. */
|
||||
radius = 6372.8 /*earth's mean radius in km */
|
||||
ph1 = d2r(ph1-ph2) /*convert degs──►radians & reduce*/
|
||||
ph2 = d2r(ph2) /* " " " " " */
|
||||
th1 = d2r(th1) /* " " " " " */
|
||||
th2 = d2r(th2)
|
||||
x = cos(ph1) * cos(th1) - cos(th2)
|
||||
y = sin(ph1) * cos(th1)
|
||||
z = sin(th1) - sin(th2)
|
||||
return radius * 2 * aSin(sqrt(x**2+y**2+z**2)/2 )
|
||||
/*═════════════════════════════general 1-line subs══════════════════════*/
|
||||
d2d: return arg(1) // 360 /*normalize degrees. */
|
||||
d2r: return r2r(arg(1)*pi() / 180) /*normalize and convert deg──►rad*/
|
||||
r2d: return d2d((arg(1)*180 / pi())) /*normalize and convert rad──►deg*/
|
||||
r2r: return arg(1) // (2*pi()) /*normalize radians. */
|
||||
p: return word(arg(1),1) /*pick the first of two words. */
|
||||
pi: if $.pipi=='' then $.pipi=$pi(); return $.pipi /*return π.*/
|
||||
|
||||
aCos: procedure expose $.; arg x; if x<-1|x>1 then call $81r -1,1,x,"ACOS"
|
||||
return .5*pi()-aSin(x) /*$81R says arg is out of range,*/
|
||||
/* and it isn't included here.*/
|
||||
aSin: procedure expose $.; parse arg x
|
||||
if x<-1 | x>1 then call $81r -1,1,x,"ASIN"; s=x*x
|
||||
if abs(x)>=.7 then return sign(x)*aCos(sqrt(1-s),'-ASIN')
|
||||
z=x; o=x; p=z; do j=2 by 2; o=o*s*(j-1)/j; z=z+o/(j+1)
|
||||
if z=p then leave; p=z; end; return z
|
||||
|
||||
cos: procedure expose $.; parse arg x; x=r2r(x); a=abs(x)
|
||||
numeric fuzz min(9,digits()-9); if a=pi() then return -1
|
||||
if a=pi()/2 | a=2*pi() then return 0; if a=pi()/3 then return .5
|
||||
if a=2*pi()/3 then return -.5; return .sinCos(1,1,-1)
|
||||
|
||||
sin: procedure expose $.; parse arg x; x=r2r(x);
|
||||
numeric fuzz min(5,digits()-3)
|
||||
if abs(x)=pi() then return 0; return .sinCos(x,x,1)
|
||||
|
||||
.sinCos: parse arg z,_,i; x=x*x; p=z; do k=2 by 2; _=-_*x/(k*(k+i)); z=z+_
|
||||
if z=p then leave; p=z; end; return z /*used by SIN & COS.*/
|
||||
|
||||
sqrt: procedure; parse arg x; if x=0 then return 0; d=digits()
|
||||
numeric digits 11; g=.sqrtGuess(); do j=0 while p>9; m.j=p; p=p%2+1; end
|
||||
do k=j+5 to 0 by -1; if m.k>11 then numeric digits m.k; g=.5*(g+x/g);end
|
||||
numeric digits d; return g/1
|
||||
.sqrtGuess: numeric form; m.=11; p=d+d%4+2
|
||||
parse value format(x,2,1,,0) 'E0' with g 'E' _ .; return g*.5'E'_%2
|
||||
|
||||
$pi: return ,
|
||||
'3.1415926535897932384626433832795028841971693993751058209749445923078'||,
|
||||
'164062862089986280348253421170679821480865132823066470938446095505822'||,
|
||||
'3172535940812848111745028410270193852110555964462294895493038196'
|
||||
/*┌───────────────────────────────────────────────────────────────────────┐
|
||||
│ A note on built-in functions. REXX doesn't have a lot of mathmatical │
|
||||
│ or (particularly) trigomentric functions, so REXX programmers have │
|
||||
│ to write their own. Usually, this is done once, or most likely, one │
|
||||
│ is borrowed from another program. Knowing this, the one that is used │
|
||||
│ has a lot of boilerplate in it. Once coded and throughly debugged, I │
|
||||
│ put those commonly-used subroutines into the "1-line sub" section. │
|
||||
│ │
|
||||
│ Programming note: the "general 1-line" subroutines are taken from │
|
||||
│ other programs that I wrote, but I broke up their one line of source │
|
||||
│ so it can be viewed without shifting the viewing window. │
|
||||
│ │
|
||||
│ The "er 81" [which won't happen here] just shows an error telling │
|
||||
│ the legal range for ARCxxx functions (in this case: -1 ──► +1). │
|
||||
│ │
|
||||
│ Similarly, the SQRT function checks for a negative argument │
|
||||
│ [which again, won't happen here]. │
|
||||
│ │
|
||||
│ The pi constant (as used here) is actually a much more robust function│
|
||||
│ and will return up to one million digits in the real version. │
|
||||
│ │
|
||||
│ One bad side effect is that, like a automobile without a hood, you see│
|
||||
│ all the dirty stuff going on. Also, don't visit a sausage factory. │
|
||||
└───────────────────────────────────────────────────────────────────────┘ */
|
||||
15
Task/Haversine-formula/Racket/haversine-formula.rkt
Normal file
15
Task/Haversine-formula/Racket/haversine-formula.rkt
Normal file
|
|
@ -0,0 +1,15 @@
|
|||
#lang racket
|
||||
(require math)
|
||||
(define earth-radius 6371)
|
||||
|
||||
(define (distance lat1 long1 lat2 long2)
|
||||
(define (h a b) (sqr (sin (/ (- b a) 2))))
|
||||
(* 2 earth-radius
|
||||
(asin (sqrt (+ (h lat1 lat2)
|
||||
(* (cos lat1) (cos lat2) (h long1 long2)))))))
|
||||
|
||||
(define (deg-to-rad d m s)
|
||||
(* (/ pi 180) (+ d (/ m 60) (/ s 3600))))
|
||||
|
||||
(distance (deg-to-rad 36 7.2 0) (deg-to-rad 86 40.2 0)
|
||||
(deg-to-rad 33 56.4 0) (deg-to-rad 118 24.0 0))
|
||||
18
Task/Haversine-formula/Ruby/haversine-formula.rb
Normal file
18
Task/Haversine-formula/Ruby/haversine-formula.rb
Normal file
|
|
@ -0,0 +1,18 @@
|
|||
include Math
|
||||
|
||||
Radius = 6371 # rough radius of the Earth, in kilometers
|
||||
|
||||
def spherical_distance(start_coords, end_coords)
|
||||
lat1, long1 = deg2rad *start_coords
|
||||
lat2, long2 = deg2rad *end_coords
|
||||
2 * Radius * asin(sqrt(sin((lat2-lat1)/2)**2 + cos(lat1) * cos(lat2) * sin((long2 - long1)/2)**2))
|
||||
end
|
||||
|
||||
def deg2rad(lat, long)
|
||||
[lat * PI / 180, long * PI / 180]
|
||||
end
|
||||
|
||||
bna = [36.12, -86.67]
|
||||
lax = [33.94, -118.4]
|
||||
|
||||
puts "%.1f" % spherical_distance(bna, lax)
|
||||
18
Task/Haversine-formula/Scala/haversine-formula.scala
Normal file
18
Task/Haversine-formula/Scala/haversine-formula.scala
Normal file
|
|
@ -0,0 +1,18 @@
|
|||
import math._
|
||||
|
||||
object Haversine {
|
||||
val R = 6372.8 //radius in km
|
||||
|
||||
def haversine(lat1:Double, lon1:Double, lat2:Double, lon2:Double)={
|
||||
val dLat=(lat2 - lat1).toRadians
|
||||
val dLon=(lon2 - lon1).toRadians
|
||||
|
||||
val a = pow(sin(dLat/2),2) + pow(sin(dLon/2),2) * cos(lat1.toRadians) * cos(lat2.toRadians)
|
||||
val c = 2 * asin(sqrt(a))
|
||||
R * c
|
||||
}
|
||||
|
||||
def main(args: Array[String]): Unit = {
|
||||
println(haversine(36.12, -86.67, 33.94, -118.40))
|
||||
}
|
||||
}
|
||||
12
Task/Haversine-formula/Scheme/haversine-formula.ss
Normal file
12
Task/Haversine-formula/Scheme/haversine-formula.ss
Normal file
|
|
@ -0,0 +1,12 @@
|
|||
(define earth-radius 6371)
|
||||
(define pi (acos -1))
|
||||
|
||||
(define (distance lat1 long1 lat2 long2)
|
||||
(define (h a b) (expt (sin (/ (- b a) 2)) 2))
|
||||
(* 2 earth-radius (asin (sqrt (+ (h lat1 lat2) (* (cos lat1) (cos lat2) (h long1 long2)))))))
|
||||
|
||||
(define (deg-to-rad d m s) (* (/ pi 180) (+ d (/ m 60) (/ s 3600))))
|
||||
|
||||
(distance (deg-to-rad 36 7.2 0) (deg-to-rad 86 40.2 0)
|
||||
(deg-to-rad 33 56.4 0) (deg-to-rad 118 24.0 0))
|
||||
; 2886.444442837984
|
||||
17
Task/Haversine-formula/Tcl/haversine-formula.tcl
Normal file
17
Task/Haversine-formula/Tcl/haversine-formula.tcl
Normal file
|
|
@ -0,0 +1,17 @@
|
|||
package require Tcl 8.5
|
||||
proc haversineFormula {lat1 lon1 lat2 lon2} {
|
||||
set rads [expr atan2(0,-1)/180]
|
||||
set R 6372.8 ;# In kilometers
|
||||
|
||||
set dLat [expr {($lat2-$lat1) * $rads}]
|
||||
set dLon [expr {($lon2-$lon1) * $rads}]
|
||||
set lat1 [expr {$lat1 * $rads}]
|
||||
set lat2 [expr {$lat2 * $rads}]
|
||||
|
||||
set a [expr {sin($dLat/2)**2 + sin($dLon/2)**2*cos($lat1)*cos($lat2)}]
|
||||
set c [expr {2*asin(sqrt($a))}]
|
||||
return [expr {$R * $c}]
|
||||
}
|
||||
|
||||
# Don't bother with too much inappropriate accuracy!
|
||||
puts [format "distance=%.1f km" [haversineFormula 36.12 -86.67 33.94 -118.40]]
|
||||
Loading…
Add table
Add a link
Reference in a new issue