Вы можете получить год от datetime.now()
и вычитать 1:
from datetime import datetime
date = datetime.strptime('Wed 12 Nov {}'.format(datetime.now().year-1), '%a %d %b %Y')
Это не будет работать на 29 февраля
На самом деле ошибка в первом варианте осуществления, он начинал в понедельник, потому что 12 ноябре 1900 был понедельник:
dte = 'Wed 12 Nov'
start = datetime.strptime('Wed 12 Nov', "%a %d %b")
greatest = None
while start <= datetime.now():
start += timedelta(days=1)
if start.strftime("%a %d %b") == dte:
greatest = start
print(greatest)
2014-11-12 00:00:00
Существует также monthdelta пакет, который вы можете использовать для увеличения в месяц:
from datetime import datetime
from monthdelta import monthdelta
dte = 'Wed 12 Nov'
start = datetime.strptime('Wed 12 Nov', "%a %d %b")
greatest = None
while start <= datetime.now():
start += monthdelta(1)
if start.strftime("%a %d %b") == dte:
greatest = start
print(greatest)
Вы можете увидеть увеличивающиеся месяцами гораздо более эффективным:
In [1]: from datetime import datetime, timedelta
In [2]: %%timeit
...: dte = 'Wed 12 Nov'
...: start = datetime.strptime('Wed 12 Nov', "%a %d %b")
...: greatest = None
...: while start <= datetime.now():
...: start += timedelta(days=1)
...: if start.strftime("%a %d %b") == dte:
...: greatest = start
...:
1 loops, best of 3: 382 ms per loop
In [3]: from datetime import datetime
In [4]: from monthdelta import monthdelta
In [5]: %%timeit
...: dte = 'Wed 12 Nov'
...: start = datetime.strptime('Wed 12 Nov', "%a %d %b")
...: greatest = None
...: while start <= datetime.now():
...: start += monthdelta(1)
...: if start.strftime("%a %d %b") == dte:
...: greatest = start
...:
100 loops, best of 3: 18.7 ms per loop
Оба возвращают довольно быстро, но если у вас было много вызовов метода, то ежемесячный рост является лучшим вариантом. Мы могли бы также добавить 30 дней, а затем установить на следующий день до 12, могут быть ошибки, как я не слишком тестировал:
def match_date(abb_wk_dy, day_date, abb_mon):
dte = "{} {} {}".format(abb_wk_dy.capitalize(), day_date, abb_mon.capitalize())
start = datetime.strptime(dte, "%a %d %b")
greatest = None
while start <= datetime.now():
start += timedelta(days=30)
start = start.strptime("{} {} {}".format(start.year, start.month, day_date), "%Y %m %d")
if start.strftime("%a %d %b") == dte:
greatest = start
return greatest
Последний код работает довольно эффективно:
In [12]: timeit match_date("wed","12","nov")
10 loops, best of 3: 34.7 ms per loop
Если вы хочу только год, а затем вернуть greatest.year
.
На тестировании выше код не високосные годы, поэтому мы должны поймать, что мы можем просто увеличить за год на 1 каждый раз:
def match_date(abb_wk_dy, day_date, abb_mon):
wkd, dd, ab = abb_wk_dy.capitalize(), day_date, abb_mon.capitalize()
match = "{} {} {}".format(wkd, dd, ab)
try:
dte = "{} {} {} {}".format(1900, wkd, dd, ab)
start = datetime.strptime(dte, "%Y %a %d %b")
except ValueError:
# first leap year since 1900
dte = "{} {} {} {}".format(1904, wkd, dd, ab)
start = datetime.strptime(dte, "%Y %a %d %b")
day, mon = start.day, start.month
greatest = None
while start <= datetime.now():
try:
start = start.strptime("{} {} {}".format(start.year + 1, mon, day), "%Y %m %d")
except ValueError:
start = start.strptime("{} {} {}".format(start.year + 1, 01, 01), "%Y %m %d")
continue
if start.strftime("%a %d %b") == match:
greatest = start
return greatest.year if greatest else "No match"
который работает в:
In [27]: timeit match_date("Wed","12","Nov")
100 loops, best of 3: 2.63 ms per loop
Вам также нужно будет подтвердить, что ни один день> 31 никогда не вводится, а другие месяцы и дни совпадают, что может быть достигнуто с помощью dict или calender.monthrange
или максимального количества карт, отображающих максимальный день в месяц-месяц.
Я думаю, что OP хочет этого, если (input_month, input_day) является * после * (today_month, today_day) - но если (input_month, input_day) уже произошло в этом году, они хотят (today_year) - но я, безусловно, читая больше в вопросе, чем было написано. – jedwards
@jedwards, я думал по тем же строкам, но это не совсем ясно, простая проверка, если текущий день и месяц> затем использовать текущий год, должен работать, если это так. –
Если у вас есть «Tue 12 Nov», 'вместо этого, это не сработает, потому что желаемый год будет в 2013 году. Ключ находится в день недели. –