在当前日期加一年

我从 资料库中提取了一个 约会,其中包含以下 变量

{{ i.operation_date }}

我得到了一个类似的价值

April 1, 2013

我需要增加一年以上,以便我可以得到

April 1, 2014

请建议,我该怎么做?

167759 次浏览

convert it into python datetime object if it isn't already. then add deltatime

one_years_later = Your_date + datetime.timedelta(days=(years*days_per_year))

for your case days=365.

you can have condition to check if the year is leap or no and adjust days accordingly

you can add as many years as you want

You can use Python-dateutil's relativedelta to increment a datetime object while remaining sensitive to things like leap years and month lengths. Python-dateutil comes packaged with matplotlib if you already have that. You can do the following:

from dateutil.relativedelta import relativedelta


new_date = old_date + relativedelta(years=1)

(This answer was given by @Max to a similar question).

But if your date is a string (i.e. not already a datetime object) you can convert it using datetime:

from datetime import datetime
from dateutil.relativedelta import relativedelta


your_date_string = "April 1, 2012"
format_string = "%B %d, %Y"


datetime_object = datetime.strptime(your_date_string, format_string).date()
new_date = datetime_object + relativedelta(years=1)
new_date_string = datetime.strftime(new_date, format_string).replace(' 0', ' ')

new_date_string will contain "April 1, 2013".

NB: Unfortunately, datetime only outputs day values as "decimal numbers" - i.e. with leading zeros if they're single digit numbers. The .replace() at the end is a workaround to deal with this issue copied from @Alex Martelli (see this question for his and other approaches to this problem).

It seems from your question that you would like to simply increment the year of your given date rather than worry about leap year implications. You can use the date class to do this by accessing its member year.

from datetime import date
startDate = date(2012, 12, 21)


# reconstruct date fully
endDate = date(startDate.year + 1, startDate.month, startDate.day)
# replace year only
endDate = startDate.replace(startDate.year + 1)

If you're having problems creating one given your format, let us know.

AGSM's answer shows a convenient way of solving this problem using the python-dateutil package. But what if you don't want to install that package? You could solve the problem in vanilla Python like this:

from datetime import date


def add_years(d, years):
"""Return a date that's `years` years after the date (or datetime)
object `d`. Return the same calendar date (month and day) in the
destination year, if it exists, otherwise use the following day
(thus changing February 29 to March 1).


"""
try:
return d.replace(year = d.year + years)
except ValueError:
return d + (date(d.year + years, 1, 1) - date(d.year, 1, 1))

If you want the other possibility (changing February 29 to February 28) then the last line should be changed to:

        return d + (date(d.year + years, 3, 1) - date(d.year, 3, 1))

Look at this:

#!/usr/bin/python


import datetime


def addYears(date, years):
result = date + datetime.timedelta(366 * years)
if years > 0:
while result.year - date.year > years or date.month < result.month or date.day < result.day:
result += datetime.timedelta(-1)
elif years < 0:
while result.year - date.year < years or date.month > result.month or date.day > result.day:
result += datetime.timedelta(1)
print "input: %s output: %s" % (date, result)
return result

Example usage:

addYears(datetime.date(2012,1,1), -1)
addYears(datetime.date(2012,1,1), 0)
addYears(datetime.date(2012,1,1), 1)
addYears(datetime.date(2012,1,1), -10)
addYears(datetime.date(2012,1,1), 0)
addYears(datetime.date(2012,1,1), 10)

And output of this example:

input: 2012-01-01 output: 2011-01-01
input: 2012-01-01 output: 2012-01-01
input: 2012-01-01 output: 2013-01-01
input: 2012-01-01 output: 2002-01-01
input: 2012-01-01 output: 2012-01-01
input: 2012-01-01 output: 2022-01-01

This is what I do when I need to add months or years and don't want to import more libraries. Just create a datetime.date() object, call add_month(date) to add a month and add_year(date) to add a year.

import datetime
__author__ = 'Daniel Margarido'




# Check if the int given year is a leap year
# return true if leap year or false otherwise
def is_leap_year(year):
if (year % 4) == 0:
if (year % 100) == 0:
if (year % 400) == 0:
return True
else:
return False
else:
return True
else:
return False




THIRTY_DAYS_MONTHS = [4, 6, 9, 11]
THIRTYONE_DAYS_MONTHS = [1, 3, 5, 7, 8, 10, 12]


# Inputs -> month, year Booth integers
# Return the number of days of the given month
def get_month_days(month, year):
if month in THIRTY_DAYS_MONTHS:   # April, June, September, November
return 30
elif month in THIRTYONE_DAYS_MONTHS:   # January, March, May, July, August, October, December
return 31
else:   # February
if is_leap_year(year):
return 29
else:
return 28


# Checks the month of the given date
# Selects the number of days it needs to add one month
# return the date with one month added
def add_month(date):
current_month_days = get_month_days(date.month, date.year)
next_month_days = get_month_days(date.month + 1, date.year)


delta = datetime.timedelta(days=current_month_days)
if date.day > next_month_days:
delta = delta - datetime.timedelta(days=(date.day - next_month_days) - 1)


return date + delta




def add_year(date):
if is_leap_year(date.year):
delta = datetime.timedelta(days=366)
else:
delta = datetime.timedelta(days=365)


return date + delta




# Validates if the expected_value is equal to the given value
def test_equal(expected_value, value):
if expected_value == value:
print "Test Passed"
return True


print "Test Failed : " + str(expected_value) + " is not equal to " str(value)
return False


# Test leap year
print "---------- Test leap year ----------"
test_equal(True, is_leap_year(2012))
test_equal(True, is_leap_year(2000))
test_equal(False, is_leap_year(1900))
test_equal(False, is_leap_year(2002))
test_equal(False, is_leap_year(2100))
test_equal(True, is_leap_year(2400))
test_equal(True, is_leap_year(2016))


# Test add month
print "---------- Test add month ----------"
test_equal(datetime.date(2016, 2, 1), add_month(datetime.date(2016, 1, 1)))
test_equal(datetime.date(2016, 6, 16), add_month(datetime.date(2016, 5, 16)))
test_equal(datetime.date(2016, 3, 15), add_month(datetime.date(2016, 2, 15)))
test_equal(datetime.date(2017, 1, 12), add_month(datetime.date(2016, 12, 12)))
test_equal(datetime.date(2016, 3, 1), add_month(datetime.date(2016, 1, 31)))
test_equal(datetime.date(2015, 3, 1), add_month(datetime.date(2015, 1, 31)))
test_equal(datetime.date(2016, 3, 1), add_month(datetime.date(2016, 1, 30)))
test_equal(datetime.date(2016, 4, 30), add_month(datetime.date(2016, 3, 30)))
test_equal(datetime.date(2016, 5, 1), add_month(datetime.date(2016, 3, 31)))


# Test add year
print "---------- Test add year ----------"
test_equal(datetime.date(2016, 2, 2), add_year(datetime.date(2015, 2, 2)))
test_equal(datetime.date(2001, 2, 2), add_year(datetime.date(2000, 2, 2)))
test_equal(datetime.date(2100, 2, 2), add_year(datetime.date(2099, 2, 2)))
test_equal(datetime.date(2101, 2, 2), add_year(datetime.date(2100, 2, 2)))
test_equal(datetime.date(2401, 2, 2), add_year(datetime.date(2400, 2, 2)))

Another way would be to use pandas "DateOffset" class

link:-https://pandas.pydata.org/pandas-docs/stable/reference/api/pandas.tseries.offsets.DateOffset.html

Using ASGM's code(above in the answers):

from datetime import datetime
import pandas as pd


your_date_string = "April 1, 2012"
format_string = "%B %d, %Y"


datetime_object = datetime.strptime(your_date_string, format_string).date()
new_date = datetime_object + pd.DateOffset(years=1)


new_date.date()

It will return the datetime object with the added year.

Something like this:-

datetime.date(2013, 4, 1)

Here's one more answer that I've found to be pretty concise and doesn't use external packages:

import datetime as dt
import calendar


# Today, in `dt.date` type
day = dt.datetime.now().date()


one_year_delta = dt.timedelta(days=366 if ((day.month >= 3 and calendar.isleap(day.year+1)) or
(day.month < 3 and calendar.isleap(day.year))) else 365)


# Add one year to the current date
print(day + one_year_delta)

You can replace the year in a date and get the expected result

import datetime
date_now = datetime.date.today()
years_to_add = date_now.year + 1


date_1 = date_now.strftime('%Y-%m-%d')
date_2 = date_now.replace(year=years_to_add).strftime('%Y-%m-%d')


print(date_1)
print(date_2)


# 2021-08-03
# 2022-08-03