PHP/MySQL의 지리 검색(거리) 최적화
위도-경도 쌍이 포함된 대규모 테이블에서 거리 기반 쿼리를 수행할 때, 쿼리 성능을 최적화하는 것이 중요해졌습니다. MySQL 쿼리가 직면한 다음 과제를 고려하십시오.
검색의 경계 영역
효율적인 솔루션은 관심 영역 주위에 경계 상자를 정의하는 것입니다. 그런 다음 쿼리는 이 경계 영역 내의 행을 선택하여 거리 계산 횟수를 크게 줄일 수 있습니다. Movable Type 기사는 경계 상자를 작성하고 이를 SQL 쿼리에 사용하는 방법에 대한 자세한 지침을 제공합니다.
보다 정확한 결과를 위한 Vincenty Formula
Haversine 공식이 충분하지 않은 경우 정확도가 높으면 Vincenty 공식을 배포할 수 있습니다. 이 JavaScript 예는 대원 거리 계산 구현을 보여줍니다.
// Vincenty formula to calculate great circle distance between 2 locations expressed as Lat/Long in KM function VincentyDistance($lat1,$lat2,$lon1,$lon2){ $a = 6378137 - 21 * sin($lat1); $b = 6356752.3142; $f = 1/298.257223563; $p1_lat = $lat1/57.29577951; $p2_lat = $lat2/57.29577951; $p1_lon = $lon1/57.29577951; $p2_lon = $lon2/57.29577951; $L = $p2_lon - $p1_lon; $U1 = atan((1-$f) * tan($p1_lat)); $U2 = atan((1-$f) * tan($p2_lat)); $sinU1 = sin($U1); $cosU1 = cos($U1); $sinU2 = sin($U2); $cosU2 = cos($U2); $lambda = $L; $lambdaP = 2*M_PI; $iterLimit = 20; while(abs($lambda-$lambdaP) > 1e-12 && $iterLimit>0) { $sinLambda = sin($lambda); $cosLambda = cos($lambda); $sinSigma = sqrt(($cosU2*$sinLambda) * ($cosU2*$sinLambda) + ($cosU1*$sinU2-$sinU1*$cosU2*$cosLambda) * ($cosU1*$sinU2-$sinU1*$cosU2*$cosLambda)); //if ($sinSigma==0){return 0;} // co-incident points $cosSigma = $sinU1*$sinU2 + $cosU1*$cosU2*$cosLambda; $sigma = atan2($sinSigma, $cosSigma); $alpha = asin($cosU1 * $cosU2 * $sinLambda / $sinSigma); $cosSqAlpha = cos($alpha) * cos($alpha); $cos2SigmaM = $cosSigma - 2*$sinU1*$sinU2/$cosSqAlpha; $C = $f/16*$cosSqAlpha*(4+$f*(4-3*$cosSqAlpha)); $lambdaP = $lambda; $lambda = $L + (1-$C) * $f * sin($alpha) * ($sigma + $C*$sinSigma*($cos2SigmaM+$C*$cosSigma*(-1+2*$cos2SigmaM*$cos2SigmaM))); } $uSq = $cosSqAlpha*($a*$a-$b*$b)/($b*$b); $A = 1 + $uSq/16384*(4096+$uSq*(-768+$uSq*(320-175*$uSq))); $B = $uSq/1024 * (256+$uSq*(-128+$uSq*(74-47*$uSq))); $deltaSigma = $B*$sinSigma*($cos2SigmaM+$B/4*($cosSigma*(-1+2*$cos2SigmaM*$cos2SigmaM)- $B/6*$cos2SigmaM*(-3+4*$sinSigma*$sinSigma)*(-3+4*$cos2SigmaM*$cos2SigmaM))); $s = $b*$A*($sigma-$deltaSigma); return $s/1000; } echo VincentyDistance($lat1,$lat2,$lon1,$lon2);
결론
경계 상자를 활용하고 대체 거리 계산 방법을 고려하면 크게 개선할 수 있습니다. MySQL에서의 지역 검색 쿼리 성능. 대규모 검색이든 웹 애플리케이션의 중요한 구성 요소이든 이러한 최적화는 사용자 경험을 향상시키고 효율적인 데이터베이스 운영을 보장합니다.
위 내용은 대규모 데이터세트에 대한 거리 기반 검색을 위해 PHP/MySQL에서 지역 검색 쿼리를 어떻게 최적화할 수 있나요?의 상세 내용입니다. 자세한 내용은 PHP 중국어 웹사이트의 기타 관련 기사를 참조하세요!