Cet article a été repris par la rédaction pour rendre hommage au site sametmax.com qui a tant apporté a la communauté python
Manipuler des dates, c’est chaud. Le calendrier, c’est plein de subtilités comme les années bissextiles, les mois qui ont 4 possibilités de nombre de jours, les semaines qui commencent un dimanche aux US et un lundi en France… Autant dire que faire ça à la mano, c’est pas marrant, marrant. Vous pouvez l’apprendre dans différentes formations python.
Avec les modules datetimes et calendar, c’est déjà plus cool.
Date et heure
Datetime est un module qui permet de manipuler des dates et des durées sous forme d’objets. L’idée est simple: vous manipulez l’objet pour faire tous vos calculs, et quand vous avez besoin de l’afficher, vous formatez l’objet en chaîne de caractères.
On peut créer artificiellement un objet datetime, ses paramètres sont:
datetime(année, mois, jour, heure, minute, seconde, microseconde, fuseau horaire)
Mais seuls “année”, “mois” et “jour” sont obligatoires.
from datetime import datetime
datetime(2000, 1, 1)
datetime.datetime(2000, 1, 1, 0, 0)
Nous sommes ici le premier janvier 2000, à la seconde et la minute zéro, de l’heure zéro.
On peut bien entendu récupérer l’heure et la date du jour:
maintenant = datetime.now()
maintenant
datetime.datetime(2012, 12, 24, 18, 20, 4, 534918)
maintenant.year
2012
maintenant.month
12
maintenant.day
24
maintenant.hour
18
maintenant.minute
20
maintenant.second
4
maintenant.microsecond
534918
maintenant.isocalendar() # année, semaine, jour
(2012, 52, 2)
Enfin, si vous souhaitez uniquement vous occuper de la date ou de l’heure:from datetime import date, time, datetime
date(2000, 1, 1)
datetime.date(2000, 1, 1)
time(12, 12, 12)
datetime.time(12, 12, 12)
maintenant = datetime.now()
maintenant.date()
datetime.date(2012, 12, 25)
maintenant.time()
datetime.time(15, 2, 16, 704000)
Notez que j’écris cet article le jour de Noël, en famille. Et que là mon frangin est en train d’aider ma mère à éplucher des pommes tandis que je les regarde de loin. C’est mal. Je vais leur donner un coup de main et je reviens.
Sam épluche les pommes et s’efforce de se tenir éloigné du débat sur la condition des canards gavés pour leur foie. Il quitte la table discrètement dès le premier usage de wikipédia pour défendre les volatiles
Back.
Je disais donc…
Durée
En plus de pouvoir récupérer la date du jour, on peut calculer la différence entre deux dates. Par exemple, combien de temps y a-t-il entre aujourd’hui et le premier jour de l’an 2000 ?
duree = datetime.now() – datetime(2000, 1, 1)
duree
datetime.timedelta(4741, 66999, 829132)
Et vous découvrez ici un autre objet: le timedelta. Cet objet représente une durée en jours, secondes et microsecondes.duree.days
4741
duree.seconds
67007
duree.mi
duree.microseconds duree.min
duree.microseconds
943760
duree.total_seconds() # addition de toutes les secondes + les jours
409689407.94376
On peut créer son propre timedelta:timedelta(days=3, seconds=100)
datetime.timedelta(3, 100)
Cela permet de répondre à la question : “Quelle date serons-nous dans 2 jours, 4 heures, 3 minutes, et 12 secondes ?”:datetime.now() + timedelta(days=2, hours=4, minutes=3, seconds=12)
datetime.datetime(2012, 12, 26, 22, 44, 6, 251071)
A chaque fois, un nouvel objet est retourné. En effet, les objets datetime et timedelta sont immutables. Ainsi si vous voulez utiliser une version légèrement différente d’un objet datetime, il faudra toujours en créer un nouveau. Par exemple:maintenant = datetime.now()
maintenant.replace(year=1995) # on créer un nouvel objet
datetime.datetime(1995, 12, 25, 0, 9, 46, 185000)
Vous noterez que je ne parles pas de fuseau horaire. Et bien c’est parce que l’implémentation Python est particulièrement ratée : l’API est compliquée et les données ne sont pas à jour. Il faut dire que la mesure du temps, contrairement à ce qu’on pourrait penser, n’est pas vraiment le truc le plus stable du monde, et des pays changent régulièrement leur manière de faire.
Donc je trollerai sur fuseaux dans un article plus gluant sur lequel, une fois n’est pas coutume, je taclerai Python. Restons sur les dates pures.
Autre modules
Une fois que vous maitrisez datetime, vous pouvez retourner lire notre article sur le formatage de date.
Mais ce n’est pas tout, il y d’autres modules liés à la gestion du temps en Python.
Dans la lib standard, il y a calendar.
Il permet de manipuler un calendrier comme un objet, et itérer sur les jours d’un mois, les semaines, vérifier les caractéristiques d’un jour en particulier, etc. :
import calendar
calendar.mdays # combien de jour par mois ?
[0, 31, 28, 31, 30, 31, 30, 31, 31, 30, 31, 30, 31]
calendar.isleap(2000) # est-ce une année bissextile ?
True
calendar.weekday(2000, 1, 1) # quel jour était cette date ?
5
calendar.MONDAY, calendar.TUESDAY, calendar.WEDNESDAY, calendar.THURSDAY, calendar.FRIDAY, calendar.SATURDAY, calendar.SUNDAY
(0, 1, 2, 3, 4, 5, 6)
On peut instancier un calendrier et itérer dessus:cal = calendar.Calendar()
cal.getfirstweekday()
0
list(cal.iterweekdays())
[0, 1, 2, 3, 4, 5, 6]
list(cal.itermonthdays(2000, 1))
[0, 0, 0, 0, 0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, 16, 17, 18, 19, 20, 21, 22, 23, 24, 25, 26, 27, 28, 29, 30, 31, 0, 0, 0, 0, 0, 0]
list(cal.itermonthdates(2000, 1))
[datetime.date(1999, 12, 27), datetime.date(1999, 12, 28), datetime.date(1999, 12, 29), datetime.date(1999, 12, 30), datetime.date(1999, 12, 31), datetime.date(2000, 1, 1), datetime.date(2000, 1, 2), datetime.date(2000, 1, 3), datetime.date(2000, 1, 4), datetime.date(2000, 1, 5), datetime.date(2000, 1, 6), datetime.date(2000, 1, 7), datetime.date(2000, 1, 8), datetime.date(2000, 1, 9), datetime.date(2000, 1, 10), datetime.date(2000, 1, 11), datetime.date(2000, 1, 12), datetime.date(2000, 1, 13), datetime.date(2000, 1, 14), datetime.date(2000, 1, 15), datetime.date(2000, 1, 16), datetime.date(2000, 1, 17), datetime.date(2000, 1, 18), datetime.date(2000, 1, 19), datetime.date(2000, 1, 20), datetime.date(2000, 1, 21), datetime.date(2000, 1, 22), datetime.date(2000, 1, 23), datetime.date(2000, 1, 24), datetime.date(2000, 1, 25), datetime.date(2000, 1, 26), datetime.date(2000, 1, 27), datetime.date(2000, 1, 28), datetime.date(2000, 1, 29), datetime.date(2000, 1, 30), datetime.date(2000, 1, 31), datetime.date(2000, 2, 1), datetime.date(2000, 2, 2), datetime.date(2000, 2, 3), datetime.date(2000, 2, 4), datetime.date(2000, 2, 5), datetime.date(2000, 2, 6)]
cal.monthdayscalendar(2000, 1)
[[0, 0, 0, 0, 0, 1, 2], [3, 4, 5, 6, 7, 8, 9], [10, 11, 12, 13, 14, 15, 16], [17, 18, 19, 20, 21, 22, 23], [24, 25, 26, 27, 28, 29, 30], [31, 0, 0, 0, 0, 0, 0]]
Comme souvent Python vient aussi avec de très bons modules tierces parties pour manipuler les dates:
dateutils est un datetime boosté aux hormones qui permet notamment de donnée des durées floues comme “+ 1 mois” et gérer des événements qui se répètent. Il est dans tous mes projets par défaut.
babel n’est pas spécialisé dans les dates mais dans la localisation. Le module possède des outils pour formater des dates selon le format de chaque pays, et aussi avec des formats naturels comme “il y a une minute”.
pytz est une implémentation saine de gestion des fuseaux horaires en Python. On y reviendra.