How to Calculate the Date when Given Month, DayOfWeek and WeekOfMonth? - c#

I need to calculate holidays which always occur on varying day in a certain week every year. They usually occur on a first weekday in a specific week and month.
I have these properties: Name, Month, DayOfWeek, WeekOfMonth. How do I use DateTime objects to calculate the Day that the holiday falls on?

Notice in the code below how they handle Labor Day and Thanksgiving. You'll probably have to do something like this for other holidays that don't always fall on a specific date.
I got this code from U.S. Holiday List in C#
private static HashSet<DateTime> GetHolidays(int year)
{
HashSet<DateTime> holidays = new HashSet<DateTime>();
//NEW YEARS
DateTime newYearsDate = AdjustForWeekendHoliday(new DateTime(year, 1, 1).Date);
holidays.Add(newYearsDate);
//MEMORIAL DAY -- last monday in May
DateTime memorialDay = new DateTime(year, 5, 31);
DayOfWeek dayOfWeek = memorialDay.DayOfWeek;
while (dayOfWeek != DayOfWeek.Monday)
{
memorialDay = memorialDay.AddDays(-1);
dayOfWeek = memorialDay.DayOfWeek;
}
holidays.Add(memorialDay.Date);
//INDEPENCENCE DAY
DateTime independenceDay = AdjustForWeekendHoliday(new DateTime(year, 7, 4).Date);
holidays.Add(independenceDay);
//LABOR DAY -- 1st Monday in September
DateTime laborDay = new DateTime(year, 9, 1);
dayOfWeek = laborDay.DayOfWeek;
while(dayOfWeek != DayOfWeek.Monday)
{
laborDay = laborDay.AddDays(1);
dayOfWeek = laborDay.DayOfWeek;
}
holidays.Add(laborDay.Date);
//THANKSGIVING DAY - 4th Thursday in November
var thanksgiving = (from day in Enumerable.Range(1, 30)
where new DateTime(year, 11, day).DayOfWeek == DayOfWeek.Thursday
select day).ElementAt(3);
DateTime thanksgivingDay = new DateTime(year, 11, thanksgiving);
holidays.Add(thanksgivingDay.Date);
DateTime christmasDay = AdjustForWeekendHoliday(new DateTime(year, 12, 25).Date);
holidays.Add(christmasDay);
return holidays;
}
public static DateTime AdjustForWeekendHoliday(DateTime holiday)
{
if (holiday.DayOfWeek == DayOfWeek.Saturday)
{
return holiday.AddDays(-1);
}
else if (holiday.DayOfWeek == DayOfWeek.Sunday)
{
return holiday.AddDays(1);
}
else
{
return holiday;
}
}

Related

How to get week ending date using current week?

I'm trying to get the week ending date using the current week. My problem is when the week ending date is not Friday. For ex. for the month of January 2023, the week ending date for week 5 is 31 which is Tuesday and my current code is returning Feb. 3 which is the Friday of that week.
This is the code that I've tried so far.
var today = DateTime.Today;
DateTime weekEndingDate = today.AddDays(-(int)today.DayOfWeek).AddDays(5);
What I need is when the week ending date is fall in Tuesday, It will return Tuesday.
Brute force.
using System;
DateTime dt = DateTime.Now;
var eow = GetEndOfWeek(dt);
Console.WriteLine(eow.ToString("D"));
dt = new DateTime(2022, 12, 31); // new years eve - on a Saturday
eow = GetEndOfWeek(dt);
Console.WriteLine(eow.ToString("D"));
DateTime GetEndOfWeek(DateTime date, DayOfWeek endOfWeek = DayOfWeek.Friday)
{
if (date.DayOfWeek == endOfWeek) return date;
int month = date.Month;
while (date.Month == month && date.DayOfWeek != endOfWeek)
{
date = date.AddDays(1);
}
if (month != date.Month) date = date.AddDays(-1);
return date;
}

Get all the dates of the month from Day of week

Is there any way to get all the occuring date for the particular day of the specified month and year..
For example:- If I have Day Thursday then I need all the dates of December 2016. Then collection should contain dates 1/12/2016, 8/12/2016, 15/12/2016, 22/12/2016, 29/12/2016.
You can create a function to get the list of dates of the month based on day of a particular year like
public static List<DateTime> GetDates(int year, int month,string day)
{
return Enumerable.Range(1, DateTime.DaysInMonth(year, month))
.Where(d=>new DateTime(year, month, d).ToString("dddd").Equals(day))
.Select(d => new DateTime(year, month, d)).ToList();
}
Now call this function like
var dates=GetDates(2016,12,"Thursday");
foreach(var d in dates){
Console.WriteLine(d.ToString());
}
Output will be
12/1/2016 12:00:00 AM
12/8/2016 12:00:00 AM
12/15/2016 12:00:00 AM
12/22/2016 12:00:00 AM
12/29/2016 12:00:00 AM
Now you have complete list of dates based on a day. You can further use it based on your requirements.
DateTime decFirst = new DateTime(2016, 12, 1);
int offset = (int)decFirst.DayOfWeek;
DateTime decThursday = decFirst.AddDays(offset);
Now you have the first Thursday of December, you should be able to do the rest.
Long form version...
private void button1_Click(object sender, EventArgs e)
{
List<DateTime> Thursdays = DaysOfMonth(2016, 12, DayOfWeek.Thursday);
foreach(DateTime dt in Thursdays)
{
Console.WriteLine(dt.ToString());
}
}
public static List<DateTime> DaysOfMonth(int year, int month, DayOfWeek day)
{
List<DateTime> dates = new List<DateTime>();
for (int i = 1; i <= DateTime.DaysInMonth(year, month); i++)
{
DateTime dt = new DateTime(year, month, i);
if (dt.DayOfWeek == day)
{
dates.Add(dt);
}
}
return dates;
}

Get x'th last working day (which is not a holiday) in month

How can i get for example 4th last working day (which is not a holiday) from a month ?
In August its 26.8.2015 day (Wednesday)
In September its 25.9.2015 day (Friday)
My actual code is following (i get an inspiration from here)
but i have an recursion and also it has syntax error.
static bool getLastXthWorkingDay(int x)
{
var weekends = new DayOfWeek[] { DayOfWeek.Saturday, DayOfWeek.Sunday };
int month = DateTime.Now.Month;
int year = DateTime.Now.Year;
IFormatProvider culture = new System.Globalization.CultureInfo("cs-CZ", true);
var holidays = new DateTime[] {
Convert.ToDateTime(String.Format("1.1.{0}",year),culture),
Convert.ToDateTime(String.Format("6.4.{0}",year),culture),
Convert.ToDateTime(String.Format("1.5.{0}",year),culture),
Convert.ToDateTime(String.Format("8.5.{0}",year),culture),
Convert.ToDateTime(String.Format("5.7.{0}",year),culture),
Convert.ToDateTime(String.Format("6.7.{0}",year),culture),
Convert.ToDateTime(String.Format("28.9.{0}",year),culture),
Convert.ToDateTime(String.Format("28.10.{0}",year),culture),
Convert.ToDateTime(String.Format("17.11.{0}",year),culture),
Convert.ToDateTime(String.Format("24.12.{0}",year),culture),
Convert.ToDateTime(String.Format("25.12.{0}",year),culture),
Convert.ToDateTime(String.Format("26.12.{0}",year),culture)
};
//Fetch the amount of days in your given month.
int daysInMonth = DateTime.DaysInMonth(year, month);
//Here we create an enumerable from 1 to daysInMonth,
//and ask whether the DateTime object we create belongs to a weekend day,
//if it doesn't, add it to our IEnumerable<int> collection of days.
IEnumerable<int> businessDaysInMonth = Enumerable.Range(1, daysInMonth)
.Where(d => !weekends.Contains(new DateTime(year, month, d).DayOfWeek));
var lastXthWorkingDay = businessDaysInMonth.Skip(Math.Max(0, businessDaysInMonth.Count() - x));
// This code has syntax error ") expected" but i dont see where ?
//if holidays.Contains(Convert.ToDateTime(String.Format("{0},{1},{2}", lastXthWorkingDay, month, year),culture))
//{
// getLastXthWorkingDay(x-1);
//}
//else { return true; }
}
any idea ?
Ok i think i got it. Thank you all
static int GetLastXthWorkingDay(int year, int month, int x)
{
var weekends = new DayOfWeek[] { DayOfWeek.Saturday, DayOfWeek.Sunday };
var holidays = new DateTime[] {
new DateTime(year, 4, 6),
new DateTime(year, 5, 1),
new DateTime(year, 5, 8),
new DateTime(year, 7, 5),
new DateTime(year, 7, 6),
new DateTime(year, 9, 28),
new DateTime(year, 10, 28),
new DateTime(year, 11, 17),
new DateTime(year, 12, 24),
new DateTime(year, 12, 25),
new DateTime(year, 12, 26),
};
//Fetch the amount of days in your given month.
int daysInMonth = DateTime.DaysInMonth(year, month);
//Here we create an enumerable from 1 to daysInMonth,
//and ask whether the DateTime object we create belongs to a weekend day,
//if it doesn't, add it to our IEnumerable<int> collection of days.
IEnumerable<int> businessDaysInMonth = Enumerable.Range(1, daysInMonth)
.Where(d => !weekends.Contains(new DateTime(year, month, d).DayOfWeek));
var lastXthWorkingDay = businessDaysInMonth.Skip(Math.Max(0, businessDaysInMonth.Count() - x));
foreach (var day in lastXthWorkingDay)
{
if ( holidays.Contains(new DateTime(year, month, day)) )
{
return GetLastXthWorkingDay(year, month, x + 1);
//return day-1;
}
else { return day; }
}
return 0;
}

Get range of days in a week given a certain day

Suppose my input is March 31, 2015.
How would I be able to get the days of the week that March 31, 2015 is in?
In this case, it should output:
March 29, 2015-April 4, 2015
I found something similar here but it's not quite what I'm looking for as that one takes in the week number while my input is a date itself.
DateTime date = new DateTime(2015, 3, 31);
DateTime weekFirstDay = date.AddDays(DayOfWeek.Sunday - date.DayOfWeek);
DateTime weekLastDay = weekFirstDay.AddDays(6);
Here is a way to get each value separately from a given DateTime
Week start:
public static DateTime GetWeekStartDate(DateTime value)
{
return value.AddDays(-(int)value.DayOfWeek).Date;
}
Week end:
public static DateTime GetWeekEndDate(DateTime value)
{
return value.AddDays(6 - (int)value.DayOfWeek).Date;
}
DayOfWeek firstDayOfWeek = CultureInfo.CurrentCulture.DateTimeFormat.FirstDayOfWeek;
DateTime startDate = DateTime.Now;
while (firstDayOfWeek != startDate.DayOfWeek)
{
startDate = startDate.AddDays(-1);
}
DateTime firstDay = startDate.Date;
DateTime lastDay = startDate.AddDays(6);

How to calculate financial year start and end dates from financial year's month end value?

I have a financial year's month end value 2.
How would i calculate the financial year DateTime startDate and DateTime endDate from that value?
You can do:
DateTime startDate = new DateTime(DateTime.Today.Year, 2, 1); // 1st Feb this year
DateTime endDate = new DateTime(DateTime.Today.Year+1, 2, 1).AddDays(-1); // Last day in January next year
Does that solve your problem?
I assume you mean Feb by 2.
This code should do this:
DateTime start = new DateTime(2010,2,1);
DateTime end = start.AddMonths(12).AddDays(-1);
Console.WriteLine(start);
Console.WriteLine(end);
Output:
01-Feb-10 12:00:00 AM
31-Jan-11 12:00:00 AM
Here is my version for calculating the Fiscal Year Start Date. It checks the StartMonth against the current month, and will adjust the year.
private DateTime? FiscalYearStartDate() {
int fyStartMonth = 2;
var dte = new DateTime(DateTime.Today.Year, fyStartMonth, 1); // 1st April this year
if (DateTime.Today.Month >= fyStartMonth) {
//Do nothing, since this is the correct calendar year for this Fiscal Year
} else {
//The FY start last calendar year, so subtract a year
dte = dte.AddYears(-1);
}
return dte;
}
You can easily calculate the End Date like others have done, by adding +1 Year, and then subtracting 1 Day (thanks to Johannes Rudolph).
DateTime endDate = new DateTime(DateTime.Today.Year+1, 2, 1).AddDays(-1);
If your current date is 14/01/2021
Then the Indian financial Year is 01/04/2020 to 31/03/2021
Use the following code for perfect output.
DateTime CurrentDate = DateTime.Now;
int CurrentMonth = CurrentDate.Month;
if (CurrentMonth >= 4)//4 is the first month of the financial year.
{
txtFromDate.Text = new DateTime(CurrentDate.Year, 4, 1).ToString(CS.ddMMyyyy);
txtToDate.Text = new DateTime(CurrentDate.Year + 1, 4, 1).AddDays(-1).ToString(CS.ddMMyyyy);
}
else
{
txtFromDate.Text = new DateTime(CurrentDate.Year - 1, 4, 1).ToString(CS.ddMMyyyy);
txtToDate.Text = new DateTime(CurrentDate.Year, 4, 1).AddDays(-1).ToString(CS.ddMMyyyy);
}
public static (DateTime, DateTime) GetCurrentFinacialYearDateRange()
{
if(DateTime.Now.Month >= 7)
{
DateTime startDate = new DateTime(DateTime.Today.Year, 7, 1); // 1st July this year
DateTime endDate = new DateTime(DateTime.Today.Year + 1, 7, 1).AddDays(-1); // Last day in June next year
return (startDate, endDate);
}
else
{
DateTime startDate = new DateTime(DateTime.Today.Year-1, 7, 1); // 1st July this year
DateTime endDate = new DateTime(DateTime.Today.Year, 7, 1).AddDays(-1); // Last day in June next year
return (startDate, endDate);
}
}

Categories

Resources