Decimal representation of the date with python

久々すぎる更新なのにしれ~っと。

とある筋から「decimal years」なんてのを初めて知る。2017-7-26 なら 2016.56557 という具合だ。…なんてヘンな含み持たせてもしょうがないか…。えとな。緯度経度と現在日時から、Magnetic Declination Estimated Value (磁偏差) を取得出来る NOAA のサービスがあって、これのインターフェイスが decimal years なのでした

decimal years てのは単に「12進数とか60進数なんかクソくらえ」ってだけの日付時刻表現てことね。

wikipedia みてもこの基礎以外はあんましわからない。decimal years の計算方法は英語でわんさか出て来る。

これだけ:

decimal_year.py
 1 # -*- coding: utf-8 -*-
 2 from datetime import datetime
 3 
 4 def datetime_to_decimal_year(date):
 5     """
 6     Calculates the decimal representation of a date, e.g., 2013.12.
 7     
 8     The code uses Python's datetime package to determine the fractional
 9     year. Thus, leap years are taken into account. There may still be
10     issues with time zones or daylight saving times etc..
11     
12     Parameters
13     ----------
14     date : python date instance
15         The input date (and time).
16       
17     Returns
18     -------
19     Decimal year : float
20         Decimal representation of the date.
21 
22     Examples
23     --------
24     >>> from datetime import datetime
25     >>> from decimal_year import datetime_to_decimal_year
26     >>> "%.5f" % datetime_to_decimal_year(datetime(2016, 7, 26))
27     '2016.56557'
28     """
29     st = datetime(date.year, 1, 1)
30     dur = (datetime(date.year + 1, 1, 1) - st).total_seconds()
31     return date.year + ((date - st).total_seconds()) / float(dur)
32 
33 
34 if __name__ == '__main__':
35     import doctest
36     doctest.testmod()

「単に10進表記にするだけデショ」て思ってるとそんな簡単な話でもなくて、「一年て何日デスカ」問題があってだな、そこの定義について wikipedia みてもよくわからんのですよ。けど色々徘徊してコードスニペットみてると皆上のコードと同じことしてた。つまり「今年は366日ある」で計算してる。

ちなみにこれを調べてたら天文学関係をまとめたと思しき PyAstronomy なんてのを見つけたんだけど、これの decimal years 関係は decimalYear.py。ここのコメントにある通り、元にしたのは stackoverflow てことで、PyAstronomy の作者はいわゆる専門家ではなさそうだ。(上に貼り付けたコードはもともとは decimalYear.py だったもの。)


追記:
PyAstronomy や StackOverflow の実装が time.mktime を使ってる意図を読み取れてなかったワタシは total_seconds() でなく days を使っていた。これだと時分秒を含んでいない。アホでした。今上で貼り付けられてるコードは total_seconds() に直してあるので、時分秒も考慮されまする。