I have a longitude and latitude as a string in PHP like below
49.648881
-103.575312
And I want to take that and look in an array of values to find the closest one. The array looks like
array(
'0'=>array('item1','otheritem1details....','55.645645','-42.5323'),
'1'=>array('item1','otheritem1details....','100.645645','-402.5323')
);
I want to return the array that has the closest long and lad. In this case it would be the first one (and yes I know -400 is not a a possible value).
Is there any quick and easy way to do this? I tried array searching but that didn't work.
Difference code
function distance($lat1, $lon1, $lat2, $lon2, $unit) {
$theta = $lon1 - $lon2;
$dist = sin(deg2rad($lat1)) * sin(deg2rad($lat2)) + cos(deg2rad($lat1)) * cos(deg2rad($lat2)) * cos(deg2rad($theta));
$dist = acos($dist);
$dist = rad2deg($dist);
$miles = $dist * 60 * 1.1515;
$unit = strtoupper($unit);
if ($unit == "K") {
return ($miles * 1.609344);
} else if ($unit == "N") {
return ($miles * 0.8684);
} else {
return $miles;
}
}
You need to map the distance of each item to the reference point first.
Then you sort the map and then you can tell which has the lowest (or highest if you reverse the search) distance:
$ref = array(49.648881, -103.575312);
$items = array(
'0' => array('item1','otheritem1details....','55.645645','-42.5323'),
'1' => array('item1','otheritem1details....','100.645645','-402.5323')
);
$distances = array_map(function($item) use($ref) {
$a = array_slice($item, -2);
return distance($a, $ref);
}, $items);
asort($distances);
echo 'Closest item is: ', var_dump($items[key($distances)]);
Output:
Closest item is: array(4) {
[0]=>
string(5) "item1"
[1]=>
string(21) "otheritem1details...."
[2]=>
string(9) "55.645645"
[3]=>
string(8) "-42.5323"
}
Take care you have the right order of lat and long.
The distance function (only the header slightly changed and units have been dropped):
function distance($a, $b)
{
list($lat1, $lon1) = $a;
list($lat2, $lon2) = $b;
$theta = $lon1 - $lon2;
$dist = sin(deg2rad($lat1)) * sin(deg2rad($lat2)) + cos(deg2rad($lat1)) * cos(deg2rad($lat2)) * cos(deg2rad($theta));
$dist = acos($dist);
$dist = rad2deg($dist);
$miles = $dist * 60 * 1.1515;
return $miles;
}