給定年份與月份,回傳該月天數。關鍵在於 2 月閏年判斷:
其他月份固定:4/6/9/11 月 30 天,其餘 31 天。
public int GetDaysInMonth(int year, int month)
{
if (month < 1 || month > 12) throw new ArgumentOutOfRangeException(nameof(month), "月份需 1-12");
if (month == 2)
{
bool isLeap = (year % 400 == 0) || (year % 4 == 0 && year % 100 != 0);
return isLeap ? 29 : 28;
}
// 30 天月份:4, 6, 9, 11
if (month == 4 || month == 6 || month == 9 || month == 11)
return 30;
return 31; // 1,3,5,7,8,10,12
}
public int GetDaysInMonth(int year, int month)
{
return DateTime.DaysInMonth(year, month); // 內建處理閏年、邊界檢查
}
優點: 經過大量測試、效能佳、程式碼最簡潔、無 Bug 風險。
public int GetDaysFromString(string yyyymm)
{
if (string.IsNullOrEmpty(yyyymm) || yyyymm.Length != 6)
throw new ArgumentException("格式需為 yyyymm", nameof(yyyymm));
int year = int.Parse(yyyymm.Substring(0, 4));
int month = int.Parse(yyyymm.Substring(4, 2));
return DateTime.DaysInMonth(year, month);
}
public static bool IsLeapYear(int year)
{
return (year % 400 == 0) || (year % 4 == 0 && year % 100 != 0);
// 或直接用 DateTime.IsLeapYear(year) (.NET Core 3.0+ / .NET 5+)
}
[TestMethod]
public void DaysInMonth_Test()
{
Assert.AreEqual(31, GetDaysInMonth(2024, 1));
Assert.AreEqual(29, GetDaysInMonth(2024, 2)); // 閏年
Assert.AreEqual(28, GetDaysInMonth(2023, 2)); // 平年
Assert.AreEqual(30, GetDaysInMonth(2024, 4));
Assert.AreEqual(31, GetDaysInMonth(2024, 12));
Assert.AreEqual(29, GetDaysInMonth(2000, 2)); // 世紀閏年
Assert.AreEqual(28, GetDaysInMonth(1900, 2)); // 世紀平年
}
public (DateTime Start, DateTime End) GetMonthRange(int year, int month)
{
int days = DateTime.DaysInMonth(year, month);
return (new DateTime(year, month, 1), new DateTime(year, month, days, 23, 59, 59));
}
原文連結:https://www.bianceng.cn/Programming/csharp/201410/45588.htm