Welcome to
aleprojects.com

Простые гео-вычисления

Все приведенные ниже вычисления сделаны из допущения о сферической формы земли, без учета ее эллипсоидности. Это позволяет упростить формулы и ускорить вычисления, что особенно важно для мобильных устройств (невысокая производительность процессоров, энергопотребление). Точность вычислений достаточна для большинства приложений.

Расстояние между двумя точками с заданными широтой и долготой.

Суть расчета заключается в вычислении косинуса угла между двумя векторами с началом в центре земли и концами на поверхности земли в данных точках. Векторы имеют одинаковую длину, равную среднему радиусу земли. Зная косинус угла и, соответственно, сам угол (в радианах), а также радиус земли, расстояние вычисляется как длина дуги сектора, образованного этими векторами: L = R∙γ, где R – радиус земли, γ - угол в радианах.

cos γ = cos α1 ∙ cos α2 ∙ (cos(β1 - β2) - 1) + cos(α1 - α2)

где α1, α2 – широта точек, β1, β2 – долгота точек.

L = R ∙ acos cos γ

Пояснения откуда взялась эта формула:

Начальный азимут между двумя точками с заданными широтой и долготой.

Азимут задается в градусах в пределах 0-360° (0° – направление на север). Для вычисления используется сферическая теорема косинусов. Также потребуется определение угла между векторами, образованными этими точками. Поэтому когда нужны и расстояние и азимут, то c точки зрения производительности эти два расчета выгодно объединить в одной функции.

Здесь угол φ - это азимут от точки A к точке B. α1, α2 – углы между векторами образуемыми точками A и B и осью земли, равняются π/2 - широта точек, γ - угол между векторами A и B, N - полюс земли.

В приведенных обозначениях сферическая теорема косинусов выглядит так:

cos α2 = cos α1 ∙ cos γ + sin α1 ∙ sin γ ∙ cos φ

cos φ = (cos α2 - cos α1 ∙ cos γ) / (sin α1 ∙ sin γ)

Как определяется cos γ см. выше.

Особые случаи

sin α1 = 0 - это означает, что начальная точка A находится на полюсе земли. Если широта начальной точки 90° (северный полюс), то любое направление из этой точки идет на юг. Поэтому φ = 180°. Если широта начальной точки -90° (южный полюс), то любое направление из этой точки идет на север. Поэтому φ = 0°.

sin γ = 0 - это означает, что точки A и B совпадают или находятся на диаметрально противоположных краях земли. В этом случае все направления эквивалентны и угол φ может быть произвольным. Пусть он будет равен 0°.

В некоторых случаях вычисленное значение cos φ может оказаться по модулю больше 1 на очень малую величину. Соответственно, Math.Acos(cos_phi) вернет значение Double.NaN. Чтобы этого не происходило, необходима проверка:

if (Math.Abs(cos_phi) > 1) cos_phi = Math.Truncate(cos_phi);

Метод Math.Acos(double) возвращает значение в интервале [0, π]. Чтобы получить значение в интервале [0, 2π] (или 0-360°), надо сделать следующее:

// lonA, lonB - longitudes of A and B in radians
...
double heading = Math.Acos(cos_phi);

if (Math.Abs(lonB - lonA) > Math.PI)
{
	if (lonB > 0) heading = 2 * Math.PI - heading;
}
else if (lonB < lonA) heading = 2 * Math.PI - heading;
...