python 节假日_在给定日期添加n个工作日,忽略python中的假日和周末

希望这可以帮助。它不是O(N)而是O(holidays)。此外,假期仅在偏移为正时才有效。

def add_working_days(start, working_days, holidays=()):

"""

Add working_days to start start date , skipping weekends and holidays.

:param start: the date to start from

:type start: datetime.datetime|datetime.date

:param working_days: offset in working days you want to add (can be negative)

:type working_days: int

:param holidays: iterator of datetime.datetime of datetime.date instances

:type holidays: iter(datetime.date|datetime.datetime)

:return: the new date wroking_days date from now

:rtype: datetime.datetime

:raise:

ValueError if working_days < 0 and holidays

"""

assert isinstance(start, (datetime.date, datetime.datetime)), 'start should be a datetime instance'

assert isinstance(working_days, int)

if working_days < 0 and holidays:

raise ValueError('Holidays and a negative offset is not implemented. ')

if working_days == 0:

return start

# first just add the days

new_date = start + datetime.timedelta(working_days)

# now compensate for the weekends.

# the days is 2 times plus the amount of weeks are included in the offset added to the day of the week

# from the start. This compensates for adding 1 to a friday because 4+1 // 5 = 1

new_date += datetime.timedelta(2 * ((working_days + start.weekday()) // 5))

# now compensate for the holidays

# process only the relevant dates so order the list and abort the handling when the holiday is no longer

# relevant. Check each holiday not being in a weekend, otherwise we don't mind because we skip them anyway

# next, if a holiday is found, just add 1 to the date, using the add_working_days function to compensate for

# weekends. Don't pass the holiday to avoid recursion more then 1 call deep.

for hday in sorted(holidays):

if hday < start:

# ignore holidays before start, we don't care

continue

if hday.weekday() > 4:

# skip holidays in weekends

continue

if hday <= new_date:

# only work with holidays up to and including the current new_date.

# increment using recursion to compensate for weekends

new_date = add_working_days(new_date, 1)

else:

break

return new_date

你可能感兴趣的:(python,节假日)