Как использовать линейную интерполяцию для оценки текущей позиции между двумя географическими координатами? - PullRequest
8 голосов
/ 16 ноября 2009

У меня есть следующие доступные:

  • последний зарегистрированный лат, долг с меткой времени
  • target lat, lon
  • расчетное время до цели
  • заголовок

Как я могу интерполировать расчетную позицию по времени?

Я знаю, что этого достаточно, чтобы рассчитать требуемую среднюю скорость для оставшейся части поездки. Учитывая прямолинейное расстояние, это довольно тривиально. Я знаю, что это связано с векторами, но я немного заржавел и подумал, что лучше проконсультироваться с некоторыми экспертами.

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

Целевой платформой является приложение Google Maps, поэтому у меня есть некоторые базовые функции, такие как гео-корректная функция для расстояния между двумя координатами. Язык не важен, так как я знаю много и могу портировать или адаптировать любые примеры, если это необходимо. Однако общие решения были бы предпочтительнее.


Это просто два независимых векторных вычисления?

lat<sub>estimate</sub> = lat<sub>start</sub> + (Δ<sub>lat</sub> * P)
lon<sub>estimate</sub> = lon<sub>start</sub> + (Δ<sub>lon</sub> * P)

Where:
   t<sub>estimated</sub> = the reported estimated time to target
   t<sub>elapsed</sub> = time since last time estimate
   P = t<sub>elapsed</sub> / t<sub>estimated</sub>
   Δ<sub>lat</sub> = lat<sub>reported</sub> - lat<sub>target</sub>
   Δ<sub>lon</sub> = lon<sub>reported</sub> - lon<sub>target</sub>

Ответы [ 2 ]

14 голосов
/ 16 ноября 2009

Вы хотите использовать Slerp или сферическую линейную интерполяцию.

Преобразование вашей широты и долготы в единицу 3-вектора:

p=(x,y,z)=(cos(lon)*cos(lat), sin(lon)*cos(lat), sin(lat))

Затем «Slerp» дает вам интерполяцию с постоянной скоростью вдоль поверхности единичной сферы:

theta= angle between 3-vectors p0 and p1 (e.g., cos(theta)= p0.p1)
Slerp(p0,p1,t)= ( p0*sin((1-t)*theta) + p1*sin(t*theta) ) / sin(theta)

Обратите внимание, что если тета очень близка к 0 или 180 градусам, эта формула может быть численно нестабильной. В случае с малым углом вы можете вернуться к линейной интерполяции; в случае с 180 градусами ваш путь действительно неоднозначен.

8 голосов
/ 16 ноября 2009
Lat_to_Travel  = CurLat - TargetLat
Long_to_Travel = CurLong - TargetLong
Time_to_Travel = ETA - now

Если расстояния относительно малы, вероятно, нормально предположить линейную прогрессию по этим трем измерениям (*). Затем вам нужно выбрать число промежуточных позиций для отображения, скажем, 10, и рассчитать каждую промежуточную точку соответственно

NbOfIntermediates       = 10  // for example    
Lat_at_Intermediate(n)  = CurLat + (1/NbOfIntermediates * Lat_to_travel)
Long_at_Intermediate(n) = CurLong + (1/NbOfIntermediates * Long_to_travel)
Time_at_Intermediate(n) = now + (1/NbOfIntermediates * Time_to_travel)

Самое сложное во всем этом - поддерживать единицы в порядке.

(*) Несколько соображений относительно того, можно ли предполагать линейную прогрессию ...
Очевидно, что особенности реальности физических элементов (морские течения, ветер, видимость ...) могут иметь большее значение в этом вопросе, чем геопространственная математика.
Предполагая, что транспортное средство движется с постоянной скорость, по прямой линии, [ обычно ] нормально предполагать линейность в измерении широты [технически земля не совсем сфера, это не совсем верно, но чертовски близко ]. Однако на более длинных расстояниях, которые включают относительно большое изменение широты, угловая прогрессия вдоль измерения долготы не является линейной. Причина этого заключается в том, что по мере удаления от экватора степень долготы, выраженная в линейных милях (или километрах ...), уменьшается. Следующая таблица должна дать приблизительное представление об этом эффекте для местоположений в различных широтах:

Latitude   Length of a Degree      Approximate examples
           (of longitude) in 
           nautical miles

0          60                      Kuala Lumpur, Bogota, Nairobi
20         56.5                    Mexico city, Mecca, Mumbai, Rio de Janeiro
45         42.5                    Geneva, Boston, Seattle, Beijing, Wellington (NZ)
60         30                      Oslo, Stockholm, Anchorage AK, St Petersburg Russia         

См. удобный онлайн-калькулятор , чтобы рассчитать это для определенной широты.
Другой способ получить представление об этом - увидеть, что путешествие на восток (или запад) по широте Джексонвилль, штат Флорида, или Сан-Диего, штат Калифорния, занимает 52 мили, чтобы покрыть градус долготы; на широте Монреаля или Сиэтла это займет всего 40 миль.

...