Расчет расстояния между точками

Географическое расстояние между точками в пространстве координат WGS84 является одной из базовых операций пространственного анализа. В Turf.js эта задача реализована через набор функций, главным образом через turf.distance, который вычисляет кратчайшее расстояние по поверхности Земли между двумя точками, представленными в формате GeoJSON.

Земная поверхность в геопространственных вычислениях обычно аппроксимируется сферой или эллипсоидом. В большинстве случаев Turf.js использует сферическую модель, что позволяет применять формулу гаверсинусов для вычисления ортодромического расстояния.

Базовая идея заключается в определении центрального угла между двумя точками на сфере:

[ d = 2R ()]

где:

  • ( _1, _2 ) — широты точек в радианах
  • ( ) — разница широт
  • ( ) — разница долгот
  • ( R ) — радиус Земли

Эта модель обеспечивает достаточную точность для большинства прикладных задач: навигации, геоаналитики, оценки близости объектов.

Основной метод turf.distance

Функция turf.distance принимает два объекта типа Point и возвращает расстояние между ними в выбранных единицах измерения.

turf.distance(from, to, options)

Формат входных данных

Точки задаются в формате GeoJSON:

const pointA = turf.point([55.751244, 37.618423]);
const pointB = turf.point([59.934280, 30.335099]);

Каждая точка представляет собой структуру:

{
  "type": "Feature",
  "geometry": {
    "type": "Point",
    "coordinates": [longitude, latitude]
  }
}

Важно учитывать порядок координат: сначала долгота, затем широта.

Единицы измерения расстояния

Функция поддерживает различные единицы измерения, задаваемые через параметр units.

Основные единицы

  • kilometers — километры (используется чаще всего)
  • miles — мили
  • meters — метры
  • degrees — градусы дуги
  • radians — радианы

Пример задания единиц измерения:

turf.distance(pointA, pointB, { units: "kilometers" });

При отсутствии параметра по умолчанию используется километровая шкала.

Пример вычисления расстояния между городами

const turf = require("@turf/turf");

const moscow = turf.point([37.618423, 55.751244]);
const spb = turf.point([30.335099, 59.934280]);

const result = turf.distance(moscow, spb, { units: "kilometers" });

console.log(result);

Результатом будет числовое значение, соответствующее кратчайшему расстоянию по дуге большого круга.

Особенности вычислений на сфере

Использование сферической модели приводит к ряду особенностей:

  • расстояние не является прямой линией в евклидовом смысле
  • результат зависит от выбранного радиуса Земли
  • возможны небольшие отклонения при высокоточных расчётах

Для задач, требующих повышенной точности (геодезия, кадастровые системы), применяется эллипсоидальная модель, однако Turf.js ориентирован на баланс между точностью и производительностью.

Влияние порядка координат

Ключевой особенностью GeoJSON является порядок координат [longitude, latitude]. Ошибочная инверсия приводит к значительным искажениям результатов, поскольку вычисления выполняются в радианной системе координат, напрямую зависящей от корректного размещения широты и долготы.

Пример некорректного задания:

// Ошибка: перепутаны координаты
turf.point([55.751244, 37.618423]);

Правильный вариант:

turf.point([37.618423, 55.751244]);

Расчёт расстояния в составе FeatureCollection

Часто вычисления выполняются не между отдельными точками, а внутри коллекций объектов.

const points = turf.featureCollection([
  turf.point([37.61, 55.75]),
  turf.point([30.33, 59.93]),
  turf.point([27.56, 53.90])
]);

Далее расстояния могут вычисляться попарно:

const a = points.features[0];
const b = points.features[1];
const c = points.features[2];

turf.distance(a, b, { units: "kilometers" });
turf.distance(b, c, { units: "kilometers" });

Использование в пространственной аналитике

Расстояние между точками является базовым элементом более сложных операций:

  • построение матриц расстояний
  • кластеризация объектов по близости
  • определение ближайших соседей
  • анализ доступности объектов инфраструктуры
  • маршрутизация как предварительный этап

В сочетании с другими функциями Turf.js (buffer, nearestPoint, pointsWithinPolygon) формируется полноценный аналитический инструментарий.

Оптимизация вычислений

При большом количестве точек вычисления расстояний становятся ресурсоёмкими. Основные подходы к оптимизации:

  • предварительная фильтрация по bounding box
  • сокращение числа попарных сравнений
  • использование пространственных индексов вне Turf.js
  • кэширование результатов для повторяющихся пар координат

Векторизация вычислений в JavaScript ограничена, поэтому основная нагрузка ложится на алгоритмическую оптимизацию структуры данных.

Поведение при одинаковых координатах

При совпадении координат двух точек результат всегда равен нулю:

const p = turf.point([10, 10]);

turf.distance(p, p, { units: "kilometers" }); // 0

Это поведение используется при нормализации данных и проверке дубликатов геообъектов.

Влияние единиц измерения на результат

Перевод между единицами осуществляется через фиксированные коэффициенты. Например:

  • 1 километр = 1000 метров
  • 1 миля ≈ 1.60934 километра

Смена единиц не влияет на геометрическую основу вычисления, только на масштабирование результата.

Работа с большими дистанциями

При расстояниях, охватывающих значительную часть земного шара, сферическая модель остаётся стабильной, однако возрастает влияние кривизны поверхности. В таких случаях особенно важно соблюдение корректного порядка координат и единообразия системы измерений во всём наборе данных.

Использование результата в дальнейших вычислениях

Полученное расстояние часто используется как входной параметр для:

  • построения изохрон
  • оценки стоимости маршрута
  • взвешивания графов
  • нормализации пространственных признаков в моделях анализа данных
  • фильтрации объектов по радиусу поиска