Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

How to calculate holidays for the USA

Tags:

vb.net

I need to know how to calculate USA holidays. I need a solution that works for any year. I didn't want to simply store the dates in a database that would need to be maintained.

For holidays on the weekend it needs to follow policy of the US government to adjust to a weekday. If it falls on a Saturday it is adjusted to Friday. If it falls on a Sunday it needs to be adjusted to Monday. I understand many (most?) banks in the US do it the same way.

How do I calculate a list of USA holidays?

Public Function getHolidayList(ByVal vYear As Integer) As List(Of Date)

    Dim HolidayList As New List(Of Date)

    '...fill the list with holidays 
    ' New Year's Day            Jan 1
    ' Martin Luther King, Jr. third Mon in Jan
    ' Washington's Birthday third Mon in Feb
    ' Memorial Day          last Mon in May
    ' Independence Day      July 4
    ' Labor Day             first Mon in Sept
    ' Columbus Day          second Mon in Oct
    ' Veterans Day          Nov 11
    ' Thanksgiving Day      fourth Thur in Nov
    ' Christmas Day         Dec 25

    'adjust for weekends

End Function

www.archives.gov

www.usa.gov

www.opm.gov

like image 853
D_Bester Avatar asked Aug 20 '13 03:08

D_Bester


People also ask

How are holiday dates determined?

Federal holidays are observed according to the legislation of individual states. The dates of these holidays, and others, are decided upon by each state government, not by the federal (national) government. Each state can agree on the same date that the President has proclaimed, such as Thanksgiving Day.

How do US federal holidays work?

The Federal Government provides employees with 11 paid holidays each year. 1 Private sector employers may provide these holidays off with pay, holidays off without pay, or holiday pay for working on a holiday, but they are not necessarily required to offer any of these options.

How do you calculate holiday hours?

Take the daily number of hours for a full-time employee eg. 8 hours, then multiply by the total number of holiday days in a year, including the bank holidays (whether you work on them or not). This will give you the number of holiday hours for a full-time employee.

How many holidays are in an American year?

Overview. As of June 2021, there are eleven annual federal holidays in the United States, and one additional quadrennial holiday (Inauguration Day).


2 Answers

This is one way to do it. A weakness of this method is that since the rules are hard coded I would need to change the code in the rare event that congress changed the rules. For my in-house software that is not a problem but it might be for others.

Also I don't calculate Easter since that is not a US federal holiday. See Nature (1876) Algorithm for Calculating the Date of Easter

Public Function getHolidayList(ByVal vYear As Integer) As List(Of Date)

    Dim FirstWeek As Integer = 1
    Dim SecondWeek As Integer = 2
    Dim ThirdWeek As Integer = 3
    Dim FourthWeek As Integer = 4
    Dim LastWeek As Integer = 5

    Dim HolidayList As New List(Of Date)

    '   http://www.usa.gov/citizens/holidays.shtml      
    '   http://archive.opm.gov/operating_status_schedules/fedhol/2013.asp

    ' New Year's Day            Jan 1
    HolidayList.Add(DateSerial(vYear, 1, 1))

    ' Martin Luther King, Jr. third Mon in Jan
    HolidayList.Add(GetNthDayOfNthWeek(DateSerial(vYear, 1, 1), DayOfWeek.Monday, ThirdWeek))

    ' Washington's Birthday third Mon in Feb
    HolidayList.Add(GetNthDayOfNthWeek(DateSerial(vYear, 2, 1), DayOfWeek.Monday, ThirdWeek))

    ' Memorial Day          last Mon in May
    HolidayList.Add(GetNthDayOfNthWeek(DateSerial(vYear, 5, 1), DayOfWeek.Monday, LastWeek))

    ' Independence Day      July 4
    HolidayList.Add(DateSerial(vYear, 7, 4))

    ' Labor Day             first Mon in Sept
    HolidayList.Add(GetNthDayOfNthWeek(DateSerial(vYear, 9, 1), DayOfWeek.Monday, FirstWeek))

    ' Columbus Day          second Mon in Oct
    HolidayList.Add(GetNthDayOfNthWeek(DateSerial(vYear, 10, 1), DayOfWeek.Monday, SecondWeek))

    ' Veterans Day          Nov 11
    HolidayList.Add(DateSerial(vYear, 11, 11))

    ' Thanksgiving Day      fourth Thur in Nov
    HolidayList.Add(GetNthDayOfNthWeek(DateSerial(vYear, 11, 1), DayOfWeek.Thursday, FourthWeek))

    ' Christmas Day         Dec 25
    HolidayList.Add(DateSerial(vYear, 12, 25))

    'saturday holidays are moved to Fri; Sun to Mon
    For i As Integer = 0 To HolidayList.Count - 1
        Dim dt As Date = HolidayList(i)
        If dt.DayOfWeek = DayOfWeek.Saturday Then
            HolidayList(i) = dt.AddDays(-1)
        End If
        If dt.DayOfWeek = DayOfWeek.Sunday Then
            HolidayList(i) = dt.AddDays(1)
        End If
    Next

    'return
    Return HolidayList

End Function

Private Function GetNthDayOfNthWeek(ByVal dt As Date, ByVal DayofWeek As Integer, ByVal WhichWeek As Integer) As Date
    'specify which day of which week of a month and this function will get the date
    'this function uses the month and year of the date provided

    'get first day of the given date
    Dim dtFirst As Date = DateSerial(dt.Year, dt.Month, 1)

    'get first DayOfWeek of the month
    Dim dtRet As Date = dtFirst.AddDays(6 - dtFirst.AddDays(-(DayofWeek + 1)).DayOfWeek)

    'get which week
    dtRet = dtRet.AddDays((WhichWeek - 1) * 7)

    'if day is past end of month then adjust backwards a week
    If dtRet >= dtFirst.AddMonths(1) Then
        dtRet = dtRet.AddDays(-7)
    End If

    'return
    Return dtRet

End Function
like image 150
D_Bester Avatar answered Sep 21 '22 05:09

D_Bester


Converted to C# as a console program... I needed the dates in a text file quickly:

class Program
{
    public class Holiday
    {
        public string HolidayName { get; set; }
        public DateTime Date { get; set; }

        public Holiday(string holidayName, DateTime date)
        {
            HolidayName = holidayName;
            Date = date;
        }
    }

    public static List<Holiday> getHolidayList(int vYear)
    {
        int FirstWeek = 1;
        int SecondWeek = 2;
        int ThirdWeek = 3;
        int FourthWeek = 4;
        int LastWeek = 5;

        List<Holiday> HolidayList = new List<Holiday>();

        //   http://www.usa.gov/citizens/holidays.shtml      
        //   http://archive.opm.gov/operating_status_schedules/fedhol/2013.asp

        // New Year's Day            Jan 1
        HolidayList.Add(new Holiday("NewYears", new DateTime(vYear, 1, 1)));

        // Martin Luther King, Jr. third Mon in Jan
        HolidayList.Add(new Holiday("MLK", GetNthDayOfNthWeek(new DateTime(vYear, 1, 1), DayOfWeek.Monday, ThirdWeek)));

        // Washington's Birthday third Mon in Feb
        HolidayList.Add(new Holiday("WashingtonsBDay", GetNthDayOfNthWeek(new DateTime(vYear, 2, 1), DayOfWeek.Monday, ThirdWeek)));

        // Memorial Day          last Mon in May
        HolidayList.Add(new Holiday("MemorialDay", GetNthDayOfNthWeek(new DateTime(vYear, 5, 1), DayOfWeek.Monday, LastWeek)));

        // Independence Day      July 4
        HolidayList.Add(new Holiday("IndependenceDay", new DateTime(vYear, 7, 4)));

        // Labor Day             first Mon in Sept
        HolidayList.Add(new Holiday("LaborDay", GetNthDayOfNthWeek(new DateTime(vYear, 9, 1), DayOfWeek.Monday, FirstWeek)));

        // Columbus Day          second Mon in Oct
        HolidayList.Add(new Holiday("Columbus", GetNthDayOfNthWeek(new DateTime(vYear, 10, 1), DayOfWeek.Monday, SecondWeek)));

        // Veterans Day          Nov 11
        HolidayList.Add(new Holiday("Veterans", new DateTime(vYear, 11, 11)));

        // Thanksgiving Day      fourth Thur in Nov
        HolidayList.Add(new Holiday("Thanksgiving", GetNthDayOfNthWeek(new DateTime(vYear, 11, 1), DayOfWeek.Thursday, FourthWeek)));

        // Christmas Day         Dec 25
        HolidayList.Add(new Holiday("Christmas", new DateTime(vYear, 12, 25)));

        //saturday holidays are moved to Fri; Sun to Mon
        foreach (var holiday in HolidayList)
        {
            if (holiday.Date.DayOfWeek == DayOfWeek.Saturday)
            {
                holiday.Date = holiday.Date.AddDays(-1);
            }
            if (holiday.Date.DayOfWeek == DayOfWeek.Sunday)
            {
                holiday.Date = holiday.Date.AddDays(1);
            }
        }

        //return
        return HolidayList;

    }

    private static System.DateTime GetNthDayOfNthWeek(DateTime dt, DayOfWeek dayofWeek, int WhichWeek)
    {
        //specify which day of which week of a month and this function will get the date
        //this function uses the month and year of the date provided

        //get first day of the given date
        System.DateTime dtFirst = new DateTime(dt.Year, dt.Month, 1);

        //get first DayOfWeek of the month
        System.DateTime dtRet = dtFirst.AddDays(6 - (int)dtFirst.AddDays(-1 * ((int)dayofWeek + 1)).DayOfWeek);

        //get which week
        dtRet = dtRet.AddDays((WhichWeek - 1) * 7);

        //if day is past end of month then adjust backwards a week
        if (dtRet >= dtFirst.AddMonths(1))
        {
            dtRet = dtRet.AddDays(-7);
        }

        //return
        return dtRet;

    }

    static void Main(string[] args)
    {
        for(int ii = 2013; ii < 2100; ii++)
        {
            var holidays = getHolidayList(ii);

            foreach (var holiday in holidays)
            {
                Console.WriteLine(holiday.HolidayName + ": " + holiday.Date.ToShortDateString());
            }
        }
    }
}
like image 38
Redbaran Avatar answered Sep 21 '22 05:09

Redbaran