簡體   English   中英

PHP中的Equirectangular近似

[英]Equirectangular approximation in PHP

我正在嘗試使用PHP中的equirectangular近似公式計算兩個緯度/經度坐標之間的距離,但是對於某些經度坐標,我得到的結果與我所知的正則公式(我知道是正確的)不同。

define('EARTH_RADIUS', 6371);

function equirectangularRad($latFrom, $lngFrom, $latTo, $lngTo) {
    $latDelta = $latTo - $latFrom;
    $lngDelta = $lngTo - $lngFrom;

    $x = $lngDelta * cos(($latFrom + $latTo) * .5);
    $radius = sqrt(($x * $x) + ($latDelta * $latDelta));

    return $radius * EARTH_RADIUS;
}

似乎總是通過本初子午線而不是最短距離計算距離。 即沿着赤道從坐標(lat = 0,long = -180)到(lat = 0,long = 180),距離應為零。 相反,該函數沿着赤道返回地球的周長; 大約40030公里。

問題似乎源於$lngDelta的計算,但對於任何編程語言,我能找到的所有實現都使用相同的公式。 我是否遺漏了一些重要的細節,或者這個公式真的不是胡潤的直接替代品(忽略明顯的准確度差異)?

以供參考; 這是我使用的hasrsine實現:

function haversineRad($latFrom, $lngFrom, $latTo, $lngTo) {
    $latDelta = $latTo - $latFrom;
    $lngDelta = $lngTo - $lngFrom;              

    $latSin = sin($latDelta * .5);
    $lngSin = sin($lngDelta * .5);
    $radius = 2. * asin(sqrt(($latSin * $latSin) + cos($latFrom) * cos($latTo) * ($lngSin * $lngSin)));

    return $radius * EARTH_RADIUS;
}   

我不知道你的配方在哪里。 下面的3個公式都計算2個坐標之間的距離。

等距離長方圓柱

function Equirectangular($lat1,$lng1,$lat2,$lng2){
$x = deg2rad($lng2-$lng1) * cos(deg2rad($lat1+$lat2)/2);
$y = deg2rad($lat1-$lat2);
$R = 6372.8; // gives d in km
$distance = sqrt($x*$x + $y*$y) * $R;
return $distance;
}

編輯修改Equirectangular()以考慮評論。 使用php abs()函數使lng值絕對。 當lng2從負面變為正面時,它開始從Haversine漂移。

function Equirectangular($lat1,$lng1,$lat2,$lng2){
$lng1 = abs($lng1);
$lng2 = abs($lng2);
$alpha = $lng2-$lng1;
$x = deg2rad($alpha) * cos(deg2rad($lat1+$lat2)/2);
$y = deg2rad($lat1-$lat2);
$R = 6372.8; // gives d in km
$distance = sqrt($x*$x + $y*$y) * $R;
return $distance;
}

半正矢

function Haversine($lat1,$lng1,$lat2,$lng2) {
  $deltaLat = $lat2 - $lat1 ;
  $deltaLng = $lng2 - $lng1 ;
  $earthRadius = 6372.8; // 3959 in miles.
  $alpha = $deltaLat/2;
  $beta = $deltaLng/2;
  $a = sin(deg2rad($alpha)) * sin(deg2rad($alpha)) + cos(deg2rad($lat1)) * cos(deg2rad($lat2)) * sin(deg2rad($beta)) * sin(deg2rad($beta)) ;
  $c = 2 * atan2(sqrt($a), sqrt(1-$a));
  $distance = $earthRadius * $c;
  return $distance;
} 

SphericalLawOfCosines

function SphericalLawOfCosines($lat1,$lng1,$lat2,$lng2) {
 $lat1 = deg2rad($lat1);
 $lat2 = deg2rad($lat2);
 $deltaLng = deg2rad($lng2-$lng1);
 $R = 6372.8; // gives d in km
$d = acos( sin($lat1)*sin($lat2) + cos($lat1)*cos($lat2) * cos($deltaLng) ) * $R;
return $d;
}

Equirectangular是最簡單但不太准確的。 對於其他2使用者取決於所涉及的距離。參見本答案 對於較小的距離(大約1米或更短),請使用Haversine。 對於較大距離,使用余弦球面定律。

公式的結果

0,-179到0,-179 Equirectangular 0 km Haversine 0 km

0,-179到0,-159 Equirectangular 2224.526851 km Haversine 2224.526851 km

0,-179到0,-139 Equirectangular 4449.053703 km Haversine 4449.053703 km

0,-179到0,-119 Equirectangular 6673.580554 km Haversine 6673.580554 km

0,-179到0,-99 Equirectangular 8898.107406 km Haversine 8898.107406 km

0,-179到0,-79 Equirectangular 11122.634257 km Haversine 11122.634257 km

0,-179到0,-59 Equirectangular 13347.161109 km Haversine 13347.161109 km

0,-179到0,-39 Equirectangular 15571.68796 km Haversine 15571.68796 km

0,-179到0,-19 Equirectangular 17796.214811 km Haversine 17796.214811 km

0,-179到0,1 Equirectangular 19798.288978 km Haversine 20020.741663 km

0,-179到0,21 Equirectangular 17573.762126 km Haversine 17796.214811 km

0,-179到0,41 Equirectangular 15349.235275 km Haversine 15571.68796 km

0,-179到0,61 Equirectangular 13124.708423 km Haversine 13347.161109 km

0,-179到0,81 Equirectangular 10900.181572 km Haversine 11122.634257 km

0,-179到0,101 Equirectangular 8675.654721 km Haversine 8898.107406 km

0,-179到0,121 Equirectangular 6451.127869 km Haversine 6673.580554 km

0,-179到0,141 Equirectangular 4226.601018 km Haversine 4449.053703 km

0,-179到0,161 Equirectangular 2002.074166 km Haversine 2224.526851 km

你重復使用latDelta其中一個用途是添加它們,另一個減去。

http://www.movable-type.co.uk/scripts/latlong.html

有工作的JavaScript。

翻譯..

$x = ($lngTo-$lngFrom) * cos(($latTo+$latFrom)/2);
$y = ($latTo-$latFrom)
$d = sqrt($x*$x + $y*$y) * EARTH_RADIUS;

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM