Я хочу создать функцию на С#, которая для номера недели вернет мне дни на этой неделе.
Например, для недели номер 40, как я могу получить дни: 4/10, 5/10, 6/10, 7/10, 8/10, 9/10, 10/10.
Заранее спасибо!
Я хочу создать функцию на С#, которая для номера недели вернет мне дни на этой неделе.
Например, для недели номер 40, как я могу получить дни: 4/10, 5/10, 6/10, 7/10, 8/10, 9/10, 10/10.
Заранее спасибо!
Я думаю, что это должно делать то, что вы хотите:
public static DateTime[] WeekDays(int Year, int WeekNumber)
{
DateTime start = new DateTime(Year, 1, 1).AddDays(7 * WeekNumber);
start = start.AddDays(-((int)start.DayOfWeek));
return Enumerable.Range(0, 7).Select(num => start.AddDays(num)).ToArray();
}
Хотя я рассматриваю воскресенье как первый день недели, если вы хотите, чтобы понедельник был первым днем, измените диапазон от (0,7) до (1,7).
Если вы хотите соответствовать стандарту ISO, я думаю, это должно работать:
public static DateTime[] WeekDays(int Year, int WeekNumber)
{
DateTime start = new DateTime(Year, 1, 4);
start = start.AddDays(-((int)start.DayOfWeek));
start = start.AddDays(7 * (WeekNumber - 1));
return Enumerable.Range(0, 7).Select(num => start.AddDays(num)).ToArray();
}
Примечание
Кажется, я пропустил ошибку. Текущий код был обновлен по состоянию на 30 января 2012 г., чтобы учесть этот факт, и теперь мы получаем
daysOffset
на основе вторника, который согласно Микаэль Свенсон, похоже, решил проблему. Подробности см. в этом ответе.
Большинство людей склонны понимать это неправильно, и под неправильным я подразумеваю несоответствие стандарту даты недели ISO8601 (мы часто используем его в Швеции). Этот расчет довольно странный, но он сводится к этому коду в .NET:
DateTime jan1 = new DateTime(yyyy, 1, 1);
int daysOffset = DayOfWeek.Tuesday - jan1.DayOfWeek;
DateTime firstMonday = jan1.AddDays(daysOffset);
var cal = CultureInfo.CurrentCulture.Calendar;
int firstWeek = cal.GetWeekOfYear(jan1, CalendarWeekRule.FirstFourDayWeek, DayOfWeek.Monday);
var weekNum = ww;
if (firstWeek <= 1)
{
weekNum -= 1;
}
var result = firstMonday.AddDays(weekNum * 7 + d - 1);
return result;
Он будет вычислять дату года (yyyy), номер недели (ww) и день недели (d). Для этого сначала устанавливается первое января с помощью встроенного календаря (чтобы этот код можно было настроить). Причина, по которой это немного странно, заключается в том, что 53-я неделя иногда приходится на январь, а иногда 1-я неделя приходится на декабрь.
Если вам нужно пойти другим путем, это не совсем тривиально, но здесь показан правильный способ сделать это в .NET.
var c = CultureInfo.CurrentCulture.Calendar;
// `FromDayOfWeek` fixes problem with the enumeration
// not based on Monday being the first day of the week
d = (byte)FromDayOfWeek(c.GetDayOfWeek(t));
switch (d)
{
case 1:
case 2:
case 3:
// see this for details
// http://blogs.msdn.com/shawnste/archive/2006/01/24/iso-8601-week-of-year-format-in-microsoft-net.aspx
t = t.AddDays(3);
break;
}
ww = (byte)c.GetWeekOfYear(t, CalendarWeekRule.FirstFourDayWeek, DayOfWeek.Monday);
// Adjust year when week 53 occurs in January or week 1 occurs in December
if (ww == 53 && t.Month == 1)
{
yyyy = (short)(t.Year - 1);
}
else if (ww == 1 && t.Month == 12)
{
yyyy = (short)(t.Year + 1);
}
else
{
yyyy = (short)t.Year;
}
Следующая функция поможет вам получить начальную дату по номеру недели и году.
public DateTime GetFirstDayFromWeekNumber(int weekNumber, int weekYear)
{
DateTime beginingYear = new DateTime(weekYear, 1, 1);
DateTime finalDate = new DateTime();
int maxDayOfWeek = (int)DayOfWeek.Saturday;
int yearStartDay = (int)beginingYear.DayOfWeek;
int dayDeference = maxDayOfWeek - yearStartDay;
if (weekNumber == 1)
{
finalDate = beginingYear.AddDays(-yearStartDay);
}
else if (weekNumber == 2)
{
finalDate = beginingYear.AddDays((dayDeference + 1));
}
else if (weekNumber > 2 && weekNumber <= 53)
{
finalDate = beginingYear.AddDays((dayDeference + 1) + ((weekNumber - 2)* 7));
}
return finalDate;
}