I want to find the "closest" end-of-month-date to a particular date. For instance, if the date is 4.3.2017
, 28.2.2017
is the closest date. For 20.3.2017
, 31.3.2017
is the closest date. For dates caught dead center it doesnt really matter if we pick the lower or the higher date.
From these two posts, How do I get the last day of a month? and Find the closest time from a list of times, I have been able to clobber together the following approach
public static DateTime findNearestDate(DateTime currDate)
{
List<DateTime> dates = new List<DateTime> { ConvertToLastDayOfMonth(currDate.AddMonths(-1)), ConvertToLastDayOfMonth(currDate) };
DateTime closestDate = dates[0];
long min = long.MaxValue;
foreach (DateTime date in dates)
if (Math.Abs(date.Ticks - currDate.Ticks) < min)
{
min = Math.Abs(date.Ticks - currDate.Ticks);
closestDate = date;
}
return closestDate;
}
public static DateTime ConvertToLastDayOfMonth(DateTime date)
{
return new DateTime(date.Year, date.Month, DateTime.DaysInMonth(date.Year, date.Month));
}
This works, but it seems like there is a lot of code for such a simple task. Does anybody know of a simpler, more compact, approach?
Given that there can only be two options, it seems odd to loop here.
Assuming you only have dates, rather than needing to worry about the time of day as well, it seems to me that the decision only rests on how many days are in the "current" month. So something like:
// Names adjusted to follow .NET naming conventions
public static DateTime FindNearestEndOfMonth(DateTime date)
{
int year = date.Year;
int month = date.Month;
int daysInMonth = DateTime.DaysInMonth(year, month);
return date.Day >= daysInMonth / 2
// End of current month
? new DateTime(year, month, daysInMonth)
// End of previous month
: new DateTime(year, month, 1).AddDays(-1);
}
See more on this question at Stackoverflow