2011-02-09 6 views
1

J'ai deux variables DateField et je voudrais les soustraire et retourner la différence en un nombre de mois au mois le plus proche. Comment pourrais-je faire ça?Soustraire des dates à Django?

Merci pour l'aide!

+0

Combien de temps dure l'un de vos "mois"? –

+0

Un mois serait de 30 jours, merci. – Andrew

+0

J'ai récemment trouvé relativedelta dans le paquetage python-dateutil. C'est très utile pour faire ce genre de choses: http://labix.org/python-dateutil#head-ba5ffd4df8111d1b83fc194b97ebecf837add454 – joshcartme

Répondre

3

Pour une réponse définitive à l'aide des longueurs de mois civil:

months = lambda a, b: abs((a.year - b.year) * 12 + a.month - b.month) 

Exemple:

>>> import datetime 
>>> a = datetime.date(2011, 2, 8) 
>>> b = datetime.date(2010, 5, 14) 
>>> months(a, b) 
9 

Edition, si vous souhaitez arrondir en fonction des jours trop:

months = lambda a, b: abs((a.year - b.year) * 12 + a.month - b.month) + int(abs(a.day - b.day) > 15) 

Exemple:

>>> import datetime 
>>> a = datetime.date(2011, 2, 8) 
>>> b = datetime.date(2010, 5, 14) 
>>> months(a, b) 
9 
>>> b = datetime.date(2010, 5, 30) 
>>> months(a, b) 
10 
+2

Vous devriez envisager d'utiliser la différence de date et un objet 'timedelta' à la place. – Arnaud

+0

Merci beaucoup! – Andrew

+0

L'autre réponse utilisait un objet 'timedelta', mais étant donné qu'il n'a de résolution qu'en jours (et que les informations mois/année sont perdues à ce stade), il ne semble pas y avoir moyen d'obtenir la différence réelle du mois calendaire. La division par 30 n'est qu'une approximation et l'erreur s'accumulera sur de longues périodes. – ezod

5

Les champs date sont des instances datetime.date. Vous pouvez les soustraire directement ce qui vous donnera un timedelta. Vous pouvez accéder au nombre de jours qu'un timedelta représente via timedelta.days. Disons que le self.date DateField est réglé sur il y a deux mois:

today = datetime.date.today() 
n = today - self.date 
months = int(n.days/30) 

devrait vous donner le nombre de mois dans ce cas 2. Selon la façon dont vous définissez le vous devrez arrondir plutôt mois le plus proche de la coulée à un int.

0
def date_diff: 
now = datetime.now().date() 
s=seo_job.job_end_date.replace(hour=23,minute=59,second=59).date() 
#seo_job.job_end_date an end date that is saved in db 
return (now-s) 
Questions connexes