J'utilise le module Python "datetime", à savoir:
>>> import datetime
>>> today = datetime.datetime.now()
>>> print today
2009-03-06 13:24:58.857946
et je voudrais calculer le jour de l’année qui est sensible aux années bissextiles. par exemple. Aujourd'hui (6 mars 2009) est le 65ème jour de 2009. Voici la calculatrice DateTime sur le Web .
En tout cas, je vois deux options:
Créez un tableau number_of_days_in_month = [31, 28, ...], décidez s'il s'agit d'une année bissextile, récapitulez manuellement les jours
Utilisez datetime.timedelta pour faire une estimation et ensuite une recherche binaire pour le bon jour de l'année:
.
>>> import datetime
>>> YEAR = 2009
>>> DAY_OF_YEAR = 62
>>> d = datetime.date(YEAR, 1, 1) + datetime.timedelta(DAY_OF_YEAR - 1)
Ces deux-là se sentent plutôt maladroits et j’ai le sentiment qu’il existe une façon plus "pythonique" de calculer le jour de l’année. Des idées/suggestions?
Il y a une solution très simple:
from datetime import datetime
day_of_year = datetime.now().timetuple().tm_yday
Ne pourriez-vous pas utiliser strftime
?
>>> import datetime
>>> today = datetime.datetime.now()
>>> print today
2009-03-06 15:37:02.484000
>>> today.strftime('%j')
'065'
Comme indiqué dans les commentaires, si vous souhaitez effectuer des comparaisons ou des calculs avec ce nombre, vous devez le convertir en int()
car strftime()
renvoie une chaîne. Si tel est le cas, vous feriez mieux d'utiliser DzinX's answer.
La réponse de DZinX est une excellente réponse à la question. J'ai trouvé cette question en cherchant la fonction inverse. J'ai trouvé que cela fonctionne:
import datetime
datetime.datetime.strptime('1936-077T13:14:15','%Y-%jT%H:%M:%S')
>>>> datetime.datetime(1936, 3, 17, 13, 14, 15)
datetime.datetime.strptime('1936-077T13:14:15','%Y-%jT%H:%M:%S').timetuple().tm_yday
>>>> 77
Je ne suis pas sûr de l’étiquette ici, mais j’ai pensé qu’un pointeur sur la fonction inverse pourrait être utile pour des personnes comme moi.
Je souhaite présenter les performances de différentes approches, sur Python 3.4, Linux x64. Extrait du profileur de ligne:
Line # Hits Time Per Hit % Time Line Contents
==============================================================
(...)
823 1508 11334 7.5 41.6 yday = int(period_end.strftime('%j'))
824 1508 2492 1.7 9.1 yday = period_end.toordinal() - date(period_end.year, 1, 1).toordinal() + 1
825 1508 1852 1.2 6.8 yday = (period_end - date(period_end.year, 1, 1)).days + 1
826 1508 5078 3.4 18.6 yday = period_end.timetuple().tm_yday
(...)
Donc, le plus efficace est
yday = (period_end - date(period_end.year, 1, 1)).days
Il suffit de soustraire le 1er janvier de la date:
import datetime
today = datetime.datetime.now()
day_of_year = (today - datetime.datetime(today.year, 1, 1)).days + 1
Si vous avez des raisons d'éviter l'utilisation du module datetime, ces fonctions fonctionneront.
def is_leap_year(year):
""" if year is a leap year return True
else return False """
if year % 100 == 0:
return year % 400 == 0
return year % 4 == 0
def doy(Y,M,D):
""" given year, month, day return day of year
Astronomical Algorithms, Jean Meeus, 2d ed, 1998, chap 7 """
if is_leap_year(Y):
K = 1
else:
K = 2
N = int((275 * M) / 9.0) - K * int((M + 9) / 12.0) + D - 30
return N
def ymd(Y,N):
""" given year = Y and day of year = N, return year, month, day
Astronomical Algorithms, Jean Meeus, 2d ed, 1998, chap 7 """
if is_leap_year(Y):
K = 1
else:
K = 2
M = int((9 * (K + N)) / 275.0 + 0.98)
if N < 32:
M = 1
D = N - int((275 * M) / 9.0) + K * int((M + 9) / 12.0) + 30
return Y, M, D
Ce code prend une date comme argument d'entrée et renvoie le jour de l'année.
from datetime import datetime
date = raw_input("Enter date: ") ## format is 02-02-2016
adate = datetime.datetime.strptime(date,"%d-%m-%Y")
day_of_year = adate.timetuple().tm_yday
day_of_year