每個月的第幾個星期幾轉DateTime

遊戲可能在每個月的第一、二、三或最後一個週末有分別的活動,
外國的節日也常常是以每個月的第幾個星期幾表示,譬如
母親節(Mother's Day),五月的第二個週日
感恩節(Thanksgiving Day),十一月的最後一個星期四

這裡紀錄如何將指定年月的第幾個星期幾,轉換成一般DateTime表示

GetActivityDate.jpg

 

/// <summary>
/// 取活動日
/// </summary>
/// <param name="obj">指定年月</param>
/// <param name="dowCount">星期幾計數,大於0正著數,小於0反著數</param>
/// <param name="dow">星期幾</param>
/// <returns></returns>
public static DateTime GetActivityDate(this DateTime obj, in int dowCount, in DayOfWeek dow)
{
    if (dowCount > 0)
    {
        DateTime date = new DateTime(obj.Year, obj.Month, 1).AddDays(-1);
        int targetWK = dowCount;
        int cnt = 0;

        for (int i = 0; i < 31; ++i)
        {
            date = date.AddDays(1);

            if (date.DayOfWeek == dow)
            {
                ++cnt;

                if (cnt == targetWK)
                {
                    return date;
                }
            }
        }
    }
    else if (dowCount < 0)
    {
        DateTime date = new DateTime(obj.Year, obj.Month, 1).AddMonths(1);
        int targetWK = dowCount * -1;
        int cnt = 0;

        for (int i = 0; i < 31; ++i)
        {
            date = date.AddDays(-1);

            if (date.DayOfWeek == dow)
            {
                ++cnt;

                if (cnt == targetWK)
                {
                    return date;
                }
            }
        }
    }

    return DateTime.MaxValue;
}

單元測試:
//母親節(Mother's Day),五月的第二個週日
new DateTime(DateTime.Today.Year, 5, 1).GetActivityDate(2, DayOfWeek.Sunday).ToString("yyyy/MM/dd")
"2022/05/08"
//陣亡將士紀念日(Memorial Day),五月的最後一個星期一
new DateTime(DateTime.Today.Year, 5, 1).GetActivityDate(-1, DayOfWeek.Monday).ToString("yyyy/MM/dd")
"2022/05/30"
//勞動節(Labor Day),九月的第一個星期一
new DateTime(DateTime.Today.Year, 9, 1).GetActivityDate(1, DayOfWeek.Monday).ToString("yyyy/MM/dd")
"2022/09/05"
//感恩節(Thanksgiving Day),十一月的最後一個星期四
new DateTime(DateTime.Today.Year, 11, 1).GetActivityDate(-1, DayOfWeek.Thursday).ToString("yyyy/MM/dd")
"2022/11/24"

測試正常

另外台指期的結算日常見第三個星期三(月商品結算),第三個星期五(季商品結算),也能用GetActivityDate取DateTime

實務上假日和活動日常常要再輸出到檔案,再經過人為修飾,再讓程式讀取檔案

有些節日很難程式化計算,譬如農民曆,
或西方的復活節(Pascha),每年春分月圓之後第一個星期日

arrow
arrow
    文章標籤
    程式設計 C# UnitTest
    全站熱搜
    創作者介紹
    創作者 Yang 的頭像
    Yang

    GNAySolution

    Yang 發表在 痞客邦 留言(0) 人氣()