Обратное уравнение восхода солнца - поиск мест с заданным временем восхода солнца в заданный день.

Я работаю над проектом для развлечения, где я представляю некоторые данные о сне географически. Для данного дня у меня есть дата, время засыпания этой ночью и время пробуждения на следующий день. Идея примерно как в этом xkcd комиксе . Мои попытки найти обратное уравнение восхода/заката, которое я нашел в Интернете, не увенчались успехом.

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

Я программист, поэтому моя цель - напечатать что-то вроде

>>>> locate(date = '2014-08-27', sunset = '10:00 PM', sunrise = '7:30 AM')

и вернуться

Latitude: 49.887, Longitude: 96.141

Я мог бы запрограммировать его сам, если бы достаточно разбирался в астрономии. Любая помощь приветствуется.

Там не было бы только одного места, обычно была бы линия по всему земному шару, где Солнце садится в определенное время. Длина и форма линии будут меняться в зависимости от даты и времени.
Хммм... в заданную дату и время мы должны быть в состоянии найти уравнение, которое говорит нам, где находится Солнце (возможно, координаты широты и долготы точки в тропиках, где Солнце в настоящее время находится прямо над головой. ) Затем точки восхода/заката образуют большой круг с центром в этой точке. (Кстати, этот метод использовался для отслеживания миграций птиц.)
@JamesScreech Я понимаю, что на земном шаре есть линия, где солнце садится в определенное время, но в каждой точке этой линии солнце взойдет в разное время на следующий день. Цель состоит в том, чтобы найти место, где солнце садится в одно определенное время и восходит в другое определенное время.
Я предполагаю, что вы видели вики-страницу уравнения восхода солнца. Обратите внимание, что вы хотите определить ф и λ , данный Дж с е т и Дж р я с е . Я бы предложил объединить все уравнения в одно большое, в котором есть только эти четыре переменные, а затем, поскольку ваше уравнение трансцендентно, решить его численно.
Хорошо, я укушу - вы имеете в виду местное время или UTC ? Если вы укажете местное время, часто может быть около 24 эквивалентных точек на земле — по одной для каждого часового пояса. UTC избавит от вырождения. Пара подъем/заход будет работать хорошо, но не во всех случаях. Кроме того, вы поменяли местами два номера здесь? Latitude: 96.141, Longitude: 49.887(широта больше 90°)
Кроме того, использование пары «закат/восход солнца» для определения местоположения приведет к тому, что пожилые люди (которым, как правило, нужно меньше сна) будут перемещаться в полушарие, где сейчас лето, а молодые люди — в противоположном направлении.
Я не вложил в этот комментарий никакой работы, но: 1) найдите широту, на которой продолжительность дня соответствует времени между восходом и заходом солнца (14,5 часов в вашем примере). За исключением близости к равноденствию, всегда будет такая широта. Затем просто найдите долготу, где время совпадает. Поскольку вы приняли ответ (+ вопрос довольно старый), я не буду вдаваться в подробности, но вы можете довольно легко получить продолжительность дня по склонению Солнца и довольно легко получить склонение Солнца по дню года.

Ответы (3)

Чтобы избежать головной боли, связанной с поиском примерно двух десятков похожих решений в зигзагообразных границах часовых поясов, вы можете придерживаться UTC . Если вы хотите иметь дело с местным временем - это будет немного безумно, если вы также попытаетесь включить и выключить летнее время.

Точки на земле, где центр солнца совпадает с горизонтом ( игнорируя топографию, сплюснутость, атмосферную рефракцию, конечную скорость света и другие мелкие эффекты ), — это просто круг на земле, где конус, проведенный от Солнца, пересекает сферическая Земля.

введите описание изображения здесь

вверху: сфера внутри конуса, с http://mathcentral.uregina.ca .

Но следующий шаг сложен — перейти от этого круга к координатам широты и долготы на поверхности, потому что ось наклонена, и потому что движение вокруг Солнца ускоряется и замедляется по мере того, как Земля приближается и удаляется от Солнца. Их можно аппроксимировать периодическими функциями с некоторыми коэффициентами, и это то, что вы найдете в математике за первым ответом. Для второго ответа я укажу два решения Python — PyEphem и Skyfield. Оба они просты в использовании, но вы отделены от фактической математики (в одном случае это эфемериды/таблица. Третий ответ — это действительно набор процедур НАСА/Лаборатории реактивного движения, которые высоко ценятся, но могут потребовать больше времени для вас, чтобы встать для скорости по сравнению с пакетами Python.

Ответ 1: Астрономические алгоритмы

Это то, с чем вам придется немного покопаться, но если вам нравится программировать, это может быть именно то, что вы ищете. Веб - сайт Gaisma — один из моих любимых в Интернете — он прост в использовании и представляет множество информации в понятной графике. Нажмите вокруг!

Я считаю, что этот сайт использует алгоритмы из коллекции, найденной на этом сайте NOAA . Щелкните вокруг там также. Они предоставляют электронные таблицы Excel, содержащие алгоритмы и другие ресурсы. «Основной» ресурс — сборник алгоритмов, опубликованный в книге Astronomical Algorithms — Jean Meeus . На этой странице Amazon вы можете увидеть, что есть много книг с похожими названиями. Я бы порекомендовал пойти в библиотеку, если это возможно, потому что (на мой взгляд) всегда хорошо ходить в библиотеки. Однако некоторые из них можно найти в Интернете. Например, несколько страниц из книги « Астрономические формулы для калькуляторов» (1988 г.) содержат интересное оглавление.

Ответ 2: Пакеты Python PyEphem и Skyfield

Я скопирую немного текста из этого ответа :

  1. Пакет Python PyEphem существует и хорошо поддерживается, и является pythonic-реинкарнацией XEphem . Я им не пользовался, но считаю, что он хранит достаточно информации об орбитальных параметрах в определенные эпохи для создания эфемерид, включая некоторые гравитационные возмущения. Другими словами, это гораздо больше, чем планеты, движущиеся по фиксированным эллиптическим орбитам вокруг неподвижного солнца. Поэтому я считаю, что он работает без подключения к Интернету.

  2. Я никогда не использовал его, потому что мне рекомендовали посмотреть Skyfield , и это именно то, что мне было нужно. Он загружает стандартные эфемериды JPL, которые вы выбираете, а затем просто использует их с вашего жесткого диска. Однако, чтобы иметь дело с секундами координации и другими эффектами, связанными со временем , время от времени необходимо проверять Интернет на наличие обновлений информации о секундах координации, поскольку они произвольны.

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

Пакеты Skyfield и PyEphem Python написаны и поддерживаются @BrandonRhodes.

Я включил простой скрипт Python только для того, чтобы проиллюстрировать, как можно использовать Skyfield. Если вам удобно кодировать без фигурных скобок, я настоятельно рекомендую вам попробовать. Это невероятно мощный и Pythonic.

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

примечание: вы можете включить атмосферное преломление, используя аргументы в apparent()методе. Дополнительную информацию см. в документации Skyfield API , а для обсуждения итерации с использованием методов Skyfield — особенно решения для времен — см. этот полезный ответ .

введите описание изображения здесь

def alt_lonlat(lon, lat, t):
    
    topo = earth.topos(lat, lon)
    
    alt, az, dist = topo.at(trise).observe(sun).apparent().altaz() ## apparent() args for atmospheric refraction
    
    return alt.degrees


from skyfield.api import load
import numpy as np
import matplotlib.pyplot as plt
import scipy.optimize as spo

data  = load('de421.bsp')
ts    = load.timescale()

# your example:  '2014-08-27', sunset = '10:00 PM', sunrise = '7:30 AM'

trise  = ts.utc(2014, 8, 27,  7, 30, 0)
tset   = ts.utc(2014, 8, 27, 22,  0, 0)

earth = data['earth']
sun   = data['sun']

zerozero = earth.topos(0.0, 0.0)   # gotta start looking somewhere!

alt, az, dist = zerozero.at(trise).observe(sun).apparent().altaz() ## apparent() args for atmospheric refraction

print "at trise, JD = ", trise.tt
print "at (0N, 0E) Sun's altitude: ", alt.degrees, "azimuth: ", az.degrees
print "at (0N, 0E) Sun's distance (km): ", dist.km

# Find points on equator where sun is on horizon (rise or set) at t=trise

limits   = ((0, 180.), (180, 360.))
lonzeros = []

for a, b in limits:

    answer, info = spo.brentq(alt_lonlat, a, b,
                              args=(0.0, trise),
                              full_output = True )

    if info.converged:
        lonzeros.append(answer)
        print "limits ", a, b, " converged! Found longitude (deg): ", answer
    else:
        print "limits ", a, b, "whaaaa?"
        lonzeros.append(None)

# make some curves

lats = np.linspace(-60, 60, 13)

longis = []
for lon0 in lonzeros:
    lons = []
    for lat in lats:
        
        answer, info = spo.brentq(alt_lonlat, lon0-90, lon0+90,
                                  args=(lat, trise),
                                  full_output = True )
        if info.converged:
            lons.append(answer)
        else:
            lons.append(None)

        lons = [(lon+180)%360.-180 for lon in lons]  # wraparound at +/- 180

    longis.append(lons)

plt.figure()

for lons in longis:
    plt.plot(lons, lats)

for lons in longis:
    plt.plot(lons, lats, 'ok')

plt.xlim(-180, 180)
plt.ylim(-90, 90)

plt.title("at trise, JD = " + str(trise.tt))

plt.show()

Ответ 3: Ядра SPICE

Как указал @barrycarter в этом комментарии под этим ответом , ядра JPL SPICE доступны. Я не знаком с ними, но это то, что использует НАСА, так что это должно быть довольно хорошо :)



Приложение:

Вот несколько скриншотов для Лондона, Великобритания ( Gaisma отсюда ):

введите описание изображения здесь

введите описание изображения здесь

введите описание изображения здесь

введите описание изображения здесь

@barrycarter вопрос исходит от программиста - если вы можете улучшить формулировку Answer 3: SPICE Kernelsраздела, сделайте это!
Этот ответ великолепен! Я не учитывал тонкости часовых поясов, поэтому лучше всего использовать UTC. Ответ 2 выглядит очень многообещающе, и я просто хорошо знаю Python, поэтому я попробую его, как только смогу.
Хорошо, это здорово! Если у вас есть вопросы по Python, вы можете задать их на Stackoverflow — не забудьте добавить skyfieldтег.
Но вы можете подумать о голосовании и / или принятии этого ответа, если сочтете его полезным, а затем вы можете задать новый вопрос, если хотите углубиться.

Из-за сложности проблемы (см. мой комментарий выше) и того факта, что вам нужен только грубый ответ, почему бы не попробовать рассчитать время восхода/захода Солнца, скажем, с интервалом в один градус для всей Земли, а затем сравнить их со временем у тебя есть. Если одного градуса недостаточно, вы можете использовать меньший интервал, а также использовать диапазон в сравнении (скажем, +/- 5 минут).

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

Этот подход может быть не самым эффективным, но при скорости современного компьютера это не займет много времени.

Я надеялся избежать такого подхода грубой силы. Я больше заинтересован в поиске математического решения или эффективного подхода, чем в том, каковы на самом деле местоположения.
Я бы не стал считать это подходом грубой силы. В самом строгом смысле да, но использование таблицы поиска для такого небольшого количества значений (даже каждая десятая градуса дает вам только 3600 значений) находится в пределах возможностей современных компьютеров и довольно часто используется для многих задач (см . алгоритмы, например).
@zephyr Таблица поиска была бы отличной идеей для поиска множества значений в одну и ту же дату, но вычисление одного значения для каждой даты, когда данные меняются изо дня в день, не похоже на то, что эффективно использует таблицы поиска. Я что-то неправильно понимаю?

Как говорит @Andy, в любое время вокруг Земли есть большой круг, где Солнце в настоящее время находится на горизонте, либо восходит, либо садится (или и то, и другое в двух точках (муравьиной) Арктики). Этот большой круг можно описать координатами точки, в которой Солнце находится прямо над головой (это вектор, указывающий от центра Земли к этому месту на поверхности или к Солнцу).

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

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