看起来pyephem 应该能够给我你在月球周期中所处位置的标准人类名称,给定日期——“上弦月”、“满月”、“上弦新月”、“渐亏凸月”等。
我说得对吗?
有谁知道这个问题的标准解决方案?
唉,对于像 \xe2\x80\x9cFull Moon\xe2\x80\x9d 这样的术语,除了月球完全满的那一刻之外,没有任何标准定义。这意味着,从技术上讲,月球完全满月的时刻只有一个无限小的时刻,因此,你可以向 PyEphem 询问的任何真实时刻都将是在那个完美的满月时刻之前或之后。
\n\n因此,除非您能找到满月时刻 \xe2\x80\x9cwide\xe2\x80\x9d 以秒为单位的标准定义,否则您询问的任何给定秒的实际相位要么是盈要么是亏。您可以查阅 USNO 定义了解所有详细信息:
\n\nhttp://aa.usno.navy.mil/faq/docs/moon_phases.php
\n\n由于那里的标准规定黄道经度的差异是确定相位的方法,因此您可以尝试如下操作:
\n\nimport ephem\ntau = 2.0 * ephem.pi\n\nsun = ephem.Sun()\nmoon = ephem.Moon()\nnames = [\'Waxing Crescent\', \'Waxing Gibbous\',\n \'Waning Gibbous\', \'Waning Crescent\']\n\nfor n in range(1, 31):\n s = \'2014/%d/11\' % n\n sun.compute(s)\n moon.compute(s)\n\n sunlon = ephem.Ecliptic(sun).lon\n moonlon = ephem.Ecliptic(moon).lon\n\n angle = (moonlon - sunlon) % tau\n quarter = int(angle * 4.0 // tau)\n print n, names[quarter]\nRun Code Online (Sandbox Code Playgroud)\n
这是我对自己的问题的快速而肮脏的解决方案。它假设observer与系统时区位于同一时区,但这对于我的目的来说已经足够了。
仍然感到惊讶的是,脓肿没有类似/比这更精致的东西,但也许有一个天文原因,我不够聪明,无法理解。
import ephem
def human_moon(observer):
target_date_utc = observer.date
target_date_local = ephem.localtime( target_date_utc ).date()
next_full = ephem.localtime( ephem.next_full_moon(target_date_utc) ).date()
next_new = ephem.localtime( ephem.next_new_moon(target_date_utc) ).date()
next_last_quarter = ephem.localtime( ephem.next_last_quarter_moon(target_date_utc) ).date()
next_first_quarter = ephem.localtime( ephem.next_first_quarter_moon(target_date_utc) ).date()
previous_full = ephem.localtime( ephem.previous_full_moon(target_date_utc) ).date()
previous_new = ephem.localtime( ephem.previous_new_moon(target_date_utc) ).date()
previous_last_quarter = ephem.localtime( ephem.previous_last_quarter_moon(target_date_utc) ).date()
previous_first_quarter = ephem.localtime( ephem.previous_first_quarter_moon(target_date_utc) ).date()
if target_date_local in (next_full, previous_full):
return 'Full'
elif target_date_local in (next_new, previous_new):
return 'New'
elif target_date_local in (next_first_quarter, previous_first_quarter):
return 'First Quarter'
elif target_date_local in (next_last_quarter, previous_last_quarter):
return 'Last Full Quarter'
elif previous_new < next_first_quarter < next_full < next_last_quarter < next_new:
return 'Waxing Crescent'
elif previous_first_quarter < next_full < next_last_quarter < next_new < next_first_quarter:
return 'Waxing Gibbous'
elif previous_full < next_last_quarter < next_new < next_first_quarter < next_full:
return 'Waning Gibbous'
elif previous_last_quarter < next_new < next_first_quarter < next_full < next_last_quarter:
return 'Waning Crescent'
Run Code Online (Sandbox Code Playgroud)