Анализ и тестванеCRM и платформи за данниМаркетингови инструменти

Изчислете или потърсете голямо кръгово разстояние между точки на географска ширина и дължина с помощта на формулата за хаверсинус (примери за PHP, JavaScript, Java, Python, MySQL, MSSQL)

Този месец програмирах на PHP и MySQL за ГИС. Докато проучвах темата, имах затруднения с намирането географски изчисления да намеря разстоянието между две местоположения, затова исках да ги споделя тук.

Карта на полета Европа с голямо кръгово разстояние

Най-простият начин за изчисляване на разстоянието между две точки е използването на питагоровата формула за изчисляване на хипотенузата на триъгълник (A² + B² = C²). Това е известно като Евклидово разстояние.

Това е интересно начало, но не се отнася за географията, тъй като разстоянието между линиите на ширина и дължина са не на равни разстояния един от друг. Колкото повече се приближавате до екватора, линиите на географската ширина се раздалечават. Ако използвате просто уравнение за триангулация, то може да измерва разстоянието точно на едно място и грешно на другото поради кривината на Земята.

Голям кръг Разстояние

Маршрутите, изминати на дълги разстояния около Земята, са известни като голямото кръгово разстояние. Тоест... най-късото разстояние между две точки на сфера се различава от точките на плоска карта. Комбинирайте това с факта, че линиите на географската ширина и дължина не са еднакво отдалечени… и ще получите трудно изчисление.

Ето едно фантастично видео обяснение как работят Великите кръгове.

Формулата на Haversine

Разстоянието, използващо кривината на Земята, е включено във формулата на Хаверсинус, която използва тригонометрия, за да вземе предвид кривината на Земята. Когато намирате разстоянието между 2 места на Земята (по права линия), правата линия всъщност е дъга.

Това е приложимо при въздушни полети – някога гледали ли сте действителната карта на полетите и сте забелязали, че са извити? Това е така, защото летенето в арка между две точки е по-кратко, отколкото директно до местоположението.

PHP: Изчислете разстоянието между 2 точки на географска ширина и дължина

Ето PHP формулата за изчисляване на разстоянието между две точки (заедно с преобразуването на мили спрямо километър), закръглена до два знака след десетичната запетая.

function getDistanceBetweenPointsNew($latitude1, $longitude1, $latitude2, $longitude2, $unit = 'miles') {
  $theta = $longitude1 - $longitude2; 
  $distance = (sin(deg2rad($latitude1)) * sin(deg2rad($latitude2))) + (cos(deg2rad($latitude1)) * cos(deg2rad($latitude2)) * cos(deg2rad($theta))); 
  $distance = acos($distance); 
  $distance = rad2deg($distance); 
  $distance = $distance * 60 * 1.1515; 
  switch($unit) { 
    case 'miles': 
      break; 
    case 'kilometers' : 
      $distance = $distance * 1.609344; 
  } 
  return (round($distance,2)); 
}

Променливите са:

  • $Latitude1 – променлива за географската ширина на първото ви местоположение.
  • $Longitude1 – променлива за дължината на първото ви местоположение
  • $Latitude2 – променлива за географската ширина на второто ви местоположение.
  • $Longitude2 – променлива за дължината на второто ви местоположение.
  • $единица – по подразбиране е мили. Това може да бъде актуализирано или предадено като km.

Java: Изчислете разстоянието между 2 точки на географска ширина и дължина

public static double getDistanceBetweenPointsNew(double latitude1, double longitude1, double latitude2, double longitude2, String unit) {
    double theta = longitude1 - longitude2;
    double distance = 60 * 1.1515 * (180/Math.PI) * Math.acos(
        Math.sin(latitude1 * (Math.PI/180)) * Math.sin(latitude2 * (Math.PI/180)) + 
        Math.cos(latitude1 * (Math.PI/180)) * Math.cos(latitude2 * (Math.PI/180)) * Math.cos(theta * (Math.PI/180))
    );
    if (unit.equals("miles")) {
        return Math.round(distance, 2);
    } else if (unit.equals("kilometers")) {
        return Math.round(distance * 1.609344, 2);
    } else {
        return 0;
    }
}

Променливите са:

  • географска ширина 1 – променлива за географската ширина на първото ви местоположение.
  • дължина 1 – променлива за дължината на първото ви местоположение
  • географска ширина 2 – променлива за географската ширина на второто ви местоположение.
  • дължина 2 – променлива за дължината на второто ви местоположение.
  • единица – по подразбиране е мили. Това може да бъде актуализирано или предадено като km.

JavaScript: Изчислете разстоянието между 2 точки на географска ширина и дължина

function getDistanceBetweenPoints(latitude1, longitude1, latitude2, longitude2, unit = 'miles') {
    let theta = longitude1 - longitude2;
    let distance = 60 * 1.1515 * (180/Math.PI) * Math.acos(
        Math.sin(latitude1 * (Math.PI/180)) * Math.sin(latitude2 * (Math.PI/180)) + 
        Math.cos(latitude1 * (Math.PI/180)) * Math.cos(latitude2 * (Math.PI/180)) * Math.cos(theta * (Math.PI/180))
    );
    if (unit == 'miles') {
        return Math.round(distance, 2);
    } else if (unit == 'kilometers') {
        return Math.round(distance * 1.609344, 2);
    }
}

Променливите са:

  • географска ширина 1 – променлива за географската ширина на първото ви местоположение.
  • дължина 1 – променлива за дължината на първото ви местоположение
  • географска ширина 2 – променлива за географската ширина на второто ви местоположение.
  • дължина 2 – променлива за дължината на второто ви местоположение.
  • единица – по подразбиране е мили. Това може да бъде актуализирано или предадено като km.

Python: Изчислете разстоянието между 2 точки на географска ширина и дължина

Ето формулата на Python за изчисляване на разстоянието между две точки (заедно с преобразуването на миля спрямо километър), закръглена до втория знак след десетичната запетая. Заслуга на моя син, Бил Кар, специалист по данни за OpenINSIGHTS, за кода.

from numpy import sin, cos, arccos, pi, round

def rad2deg(radians):
    degrees = radians * 180 / pi
    return degrees

def deg2rad(degrees):
    radians = degrees * pi / 180
    return radians

def getDistanceBetweenPointsNew(latitude1, longitude1, latitude2, longitude2, unit = 'miles'):
    
    theta = longitude1 - longitude2
    
    distance = 60 * 1.1515 * rad2deg(
        arccos(
            (sin(deg2rad(latitude1)) * sin(deg2rad(latitude2))) + 
            (cos(deg2rad(latitude1)) * cos(deg2rad(latitude2)) * cos(deg2rad(theta)))
        )
    )
    
    if unit == 'miles':
        return round(distance, 2)
    if unit == 'kilometers':
        return round(distance * 1.609344, 2)

Променливите са:

  • географска ширина 1 – променлива за първото ви местоположение ширина.
  • дължина 1 – променлива за първото ви местоположение дължина
  • географска ширина 2 – променлива за второто ви местоположение ширина.
  • дължина 2 – променлива за второто ви местоположение дължина.
  • единица – по подразбиране е мили. Това може да бъде актуализирано или предадено като km.

MySQL: Извличане на всички записи в обхват чрез изчисляване на разстояние в мили с помощта на географска ширина и дължина

Използването на пространствени типове данни в MySQL е по-ефективен и удобен начин за работа с географски данни, включително изчисляване на разстояния между точки. MySQL поддържа пространствени типове данни като POINT, LINESTRING, и POLYGON, заедно с пространствени функции като ST_Distance.

Когато използвате ST_Distance функция в MySQL с географски данни, представени като POINT координати, той отчита кривината на земната повърхност. Сферичният модел, използван от ST_Distance използва формулата на Хаверсин. Това приближение е подходящо за повечето практически цели, но може да въведе леки неточности за много големи разстояния.

Ето как можете да изчислите разстояния между две точки с помощта на пространствени типове данни:

  1. Създайте таблица с тип пространствени данни: Първо създайте таблица с a POINT колона за съхраняване на географски точки. Например:
CREATE TABLE locations (
    id INT AUTO_INCREMENT PRIMARY KEY,
    name VARCHAR(255),
    coordinates POINT
);

Вмъкнете вашите географски точки в тази таблица, като използвате POINT конструктор:

INSERT INTO locations (name, coordinates)
VALUES
    ('Point A', POINT(40.7128, -74.0060)), -- New York City
    ('Point B', POINT(34.0522, -118.2437)); -- Los Angeles
  1. Изчислете разстоянието с помощта на ST_Distance: Можете да изчислите разстоянието между две точки, като използвате ST_Distance функция. Ето примерна заявка за изчисляване на разстоянието между две точки:
SELECT
    id1,
    id2,
    (ST_Distance(coordinates1, coordinates2) / 1609.344) AS distance_in_miles
FROM (
    SELECT
        l1.id AS id1,
        l2.id AS id2,
        l1.coordinates AS coordinates1,
        l2.coordinates AS coordinates2
    FROM
        locations l1,
        locations l2
    WHERE
        l1.id = 1 AND l2.id = 2
) AS distances;

Сменете 1 намлява 2 с идентификаторите на двете точки, между които искате да изчислите разстоянието.

  1. Резултат: Заявката ще върне разстоянието между двете точки в мили.

Използване на типове пространствени данни и ST_Distance предоставя по-ефективен и точен начин за работа с географски данни в MySQL. Той също така опростява изчисляването на разстоянията между точките, което улеснява управлението и заявките за вашите данни.

MySQL: Извличане на всички записи в обхват чрез изчисляване на разстояние в километри с помощта на географска ширина и дължина

По подразбиране ST_Distance връща разстоянието в метри, така че просто трябва да актуализирате заявката за километри:

SELECT
    id1,
    id2,
    (ST_Distance(coordinates1, coordinates2) / 1000) AS distance_in_kilometers
FROM (
    SELECT
        l1.id AS id1,
        l2.id AS id2,
        l1.coordinates AS coordinates1,
        l2.coordinates AS coordinates2
    FROM
        locations l1,
        locations l2
    WHERE
        l1.id = 1 AND l2.id = 2
) AS distances;

Географско разстояние на Microsoft SQL Server: STDistance

Ако използвате Microsoft SQL Server, те предлагат собствена функция, STDstance за изчисляване на разстоянието между две точки с помощта на типа данни География.

DECLARE @g geography;  
DECLARE @h geography;  
SET @g = geography::STGeomFromText('LINESTRING(-122.360 47.656, -122.343 47.656)', 4326);  
SET @h = geography::STGeomFromText('POINT(-122.34900 47.65100)', 4326);  
SELECT @g.STDistance(@h);  

Съвет за шапка към Manash Sahoo, основател и старши архитект в Йон три.

Douglas Karr

Douglas Karr е CMO на OpenINSIGHTS и основателят на Martech Zone. Дъглас е помогнал на десетки успешни стартъпи на MarTech, съдействал е за надлежна проверка на над $5 милиарда в придобивания и инвестиции на Martech и продължава да помага на компаниите при прилагането и автоматизирането на техните стратегии за продажби и маркетинг. Дъглас е международно признат експерт и лектор по дигитална трансформация и MarTech. Дъглас също е публикуван автор на ръководство за манекени и книга за бизнес лидерство.

Свързани статии

Бутон "Нагоре" горе
Близо

Открит е рекламен блок

Martech Zone е в състояние да ви предостави това съдържание безплатно, тъй като осигуряваме приходи от нашия сайт чрез приходи от реклами, партньорски връзки и спонсорство. Ще сме благодарни, ако премахнете блокера си за реклами, докато разглеждате нашия сайт.