Python:查找从今天前两个月开始的日期,并在星期一开始

时间:2015-04-25 16:44:33

标签: python loops date datetime calendar

所以我是python的初学者,并且一直在使用datetime,time和timedelta库。我正在尝试创建一段代码,从大约两个月前开始给我约会(exact_two_months_date)(今天无论如何)。问题是,我想找到约会日期。两个月前,并在该周一的星期一开始实际的start_date。所以从理论上讲,实际开始日期不会恰好是两个月前。这将是从两个月前的星期一开始的一周。

Example pseudocode:
    today = '20150425' ## '%Y%m%d' ... Saturday
    exact_two_months_date = '20150225' ## EXACTLY two months ago ... Wednesday
    start_date = '20150223' ## this is the Monday of that week two months ago

那我怎么在上面找到'start_date'?如果两个月前的那一天是在周六或周日开始,那么我只想去下周一。希望这是明确的,有道理的...一旦找到开始日期,我想逐日(仅工作日)增加到'今天'。
感谢任何反馈,谢谢。

4 个答案:

答案 0 :(得分:3)

使用python-dateutil 计算日期 如果可以选择依赖第三方包,则python-dateutil提供了一种使用日期计算的便捷方法。

浏览☞ relativedelta的文档以查看大量支持的参数。一个包需要对日期进行的计算越多,dateutil之类的辅助模块就越能证明它的依赖性。有关它所提供的内容的更多灵感,请参阅☞ examples page

快速浏览:

>>> import datetime
>>> from dateutil.relativedelta import relativedelta

>>> today = datetime.date.today()
>>> two_m_ago = today - relativedelta(months=2)
>>> # print two_m_ago ~> datetime.date(2015, 2, 25)

>>> monday = two_m_ago - datetime.timedelta(days=two_m_ago.weekday())
>>> # print monday ~> datetime.date(2015, 2, 23)

通过weekday() 获取星期一 一旦我们在变量two_m_ago中得到两个月前的日期,我们就会从中减去weekday()的索引。该指数周一为0,周日为6。如果two_m_ago已经是星期一,那么减去0将不会导致任何更改。

答案 1 :(得分:1)

老实说,我觉得和datetime一起工作是我经常做的最难的事情,我犯了很多错误,所以我要去做这个,并展示一些我经常遇到的失败。到此为止。

两个限制:1)两个月前的日期,2)该周的星期一

两个月前的日期

好的,所以Python的datetime库有一个名为replace的有用方法,这似乎对它有帮助:

>>> import datetime
>>> now = datetime.date.today()
>>> today
datetime.date(2015, 4, 25)
>>> today.month
4
>>> two_months_ago = today.replace(month=today.month-2)
>>> two_months_ago
datetime.date(2015, 2, 25)
>>> two_months_ago.month
2

但是等一下:负面数字怎么样?这不会奏效:

>>> older = datetime.date(2015, 01, 01)
>>> older.replace(month=older.month-2)
Traceback (most recent call last):
  File "<stdin>", line 1, in <module>
ValueError: month must be in 1..12

所以有两种解决方案:

1)我可以构建一个向前或向后循环的1-12范围,或

2)要查找前两个月,我只能将day部分的日期替换为我所在的1st天,然后返回1天上个月和然后将上个月的那一天替换为我想要的那一天。

(如果你仔细想想,你会发现,如果我在一个月的第31天降落,那么其中任何一个都可能会出现错误,例如。这是{{1}的一部分。很难。)

datetime

嗯,让我们说我们已经接近了,我们需要加入一些错误检查,以确保我们想要的那一天是我们登陆的月份内的有效日期。最后,问题是&#34;两个月前&#34;当我们大声说出来时,意味着比我们想象的更多。

接下来,我们将对第二个问题进行分析:如何到达那周的星期一?

嗯,def previous_month(date): current_day = date.day first_day = date.replace(day=1) last_day_prev_month = first_day - datetime.timedelta(days=1) prev_month_day = last_day_prev_month.replace(day=current_day) return prev_month_day >>> today = datetime.date.today() >>> older = previous_month(today) >>> older datetime.date(2015, 3, 25) 个对象有一个工作日方法,所以这个部分不应该太难和here's a nice SO answer on how to do that

简单版本是:使用工作日整数的差异来确定使用datetime返回的天数。

外卖:与datetime.timedelta(days=days_difference)合作可能很难。

答案 2 :(得分:1)

这样的事情对你有用吗?

import datetime

today = datetime.date.today()
delta = datetime.timedelta(days=60) # ~ 2 months

thatDay = today - delta
# subtract weekdays to get monday
thatMonday = thatDay - datetime.timedelta(days=thatDay.weekday()) 

答案 3 :(得分:0)

Python中的日期操作非常令人费解。使用arrow包可以节省大量时间,从而大大简化了这些操作。

首先安装

pip install arrow

现在你的问题:

import arrow

# get local current time
now = arrow.now('local')

# move 2 months back
old = now.replace(months=-2)

# what day of the week was that?
dow = old.isoweekday()

# reset old to Monday, for instance at 9:32 in the morning (this is just an example, just to show case)
old = old.replace(days=-dow, hour=9, minute=32, second=0)

print('now is {now}, we went back to {old}'.format(now=now.isoformat(), old=old.isoformat()))

输出:

now is 2015-04-25T20:37:38.174000+02:00, we went back to 2015-02-22T09:32:00.174000+01:00

请注意,各种格式,时区等现在都是透明的,您只需要依赖一个包。