В настоящее время я пишу небольшой календарь в ASP.Net C #. В настоящее время для получения строк недель я делаю следующее для цикла:
var iWeeks = 6;
for (int w = 0; w < iWeeks; w++) {
Это прекрасно работает, однако, в одном месяце будет только 5 недель, а в некоторых редких случаях - 4.
Как рассчитать количество строк, которое потребуется для определенного месяца?
Это пример того, что я создаю:
Как видно из приведенного выше месяца, требуется всего 5 строк. Возьмите этот месяц (август 2008 г.), который начался в субботу и заканчивается в понедельник 6-й недели / ряд.
Изображение найдено в Google
Это пример того, что я создаю:
Как видно из приведенного выше месяца, требуется всего 5 строк. Возьмите этот месяц (август 2008 г.), который начался в субботу и заканчивается в понедельник 6-й недели / ряд.
Изображение найдено в Google
Вот метод, который делает это:
public int GetWeekRows(int year, int month)
{
DateTime firstDayOfMonth = new DateTime(year, month, 1);
DateTime lastDayOfMonth = new DateTime(year, month, 1).AddMonths(1).AddDays(-1);
System.Globalization.Calendar calendar = System.Threading.Thread.CurrentThread.CurrentCulture.Calendar;
int lastWeek = calendar.GetWeekOfYear(lastDayOfMonth, System.Globalization.CalendarWeekRule.FirstFourDayWeek, DayOfWeek.Monday);
int firstWeek = calendar.GetWeekOfYear(firstDayOfMonth, System.Globalization.CalendarWeekRule.FirstFourDayWeek, DayOfWeek.Monday);
return lastWeek - firstWeek + 1;
}
Вы можете настроить правило календарной недели, изменив часть System.Globalization.CalendarWeekRule.FirstFourDayWeek. Я надеюсь, что код не требует пояснений.
Как насчет того, чтобы узнать, на какой неделе будут первые и последние дни?
Месяцы в юлианском / григорианском календаре имеют одинаковое количество дней в году, кроме февраля, который может иметь 28 или 29 дней в зависимости от високосности года. Вы можете узнать количество дней в разделе «Описание» по адресу http://en.wikipedia.org/wiki/Gregorian_calendar .
Как упомянул @darkdog, у вас есть DateTime.DaysInMonth. Просто сделай это:
var days = DateTime.DaysInMonth(year, month) +
WhatDayOfWeekTheMonthStarts(year, month);
int rows = (days / 7);
if (0 < days % 7)
{
++rows;
}
Примите во внимание тот факт, что в целях глобализации / локализации некоторые части мира используют разные календари / методы организации года.
Попробуй это,
DateTime.DaysInMonth
Ну, это зависит от используемой вами культуры, но давайте предположим, что вы можете использовать Thread.CurrentThread.CurrentCulture, тогда код для получения текущей недели будет выглядеть так:
Culture culture = Thread.CurrentThread.CurrentCulture;
Calendar cal = culture.Calendar;
Int32 week = cal.GetWeekOfYear(DateTime.Today,
culture.DateTimeFormat.CalendarWeekRule,
culture.DateTimeFormat.FirstDayOfWeek);
Проверьте Calendar.GetWeekOfYear . Это должно сделать свое дело.
Есть проблема, она не соответствует правилу 4 дней по ISO 8601, но в остальном она аккуратна.
вы можете получить дни месяца, используя DateTime.DaysInMonth (int WhichYear, int WhichMonth);
Проблема не в количестве дней в месяце, а в том, сколько недель он охватывает.
Февраль в не високосном году будет иметь 28 дней, и если первый день месяца будет понедельником, февраль будет охватывать ровно 4 недели.
Однако, если первый день месяца - вторник или любой другой день недели, февраль будет охватывать 5-недельные числа.
31-дневный месяц может длиться 5 или 6 недель таким же образом. Если месяц начинается в понедельник, 31 день дает 5-недельные номера. Если месяц начинается в субботу или воскресенье, он будет охватывать номера 6 недель.
Таким образом, правильный способ получить это число - найти номер недели в первый и последний дни месяца.
Редактировать # 1 : Вот как рассчитать количество недель в данном месяце: Редактировать # 2 : Исправлены ошибки в коде
public static Int32 GetWeekForDateCurrentCulture(DateTime dt)
{
CultureInfo culture = Thread.CurrentThread.CurrentCulture;
Calendar cal = culture.Calendar;
return cal.GetWeekOfYear(dt,
culture.DateTimeFormat.CalendarWeekRule,
culture.DateTimeFormat.FirstDayOfWeek);
}
public static Int32 GetWeekSpanCountForMonth(DateTime dt)
{
DateTime firstDayInMonth = new DateTime(dt.Year, dt.Month, 1);
DateTime lastDayInMonth = firstDayInMonth.AddMonths(1).AddDays(-1);
return
GetWeekForDateCurrentCulture(lastDayInMonth)
- GetWeekForDateCurrentCulture(firstDayInMonth)
+ 1;
}
Сначала выясните, в какой день недели уходит первый день месяца. Просто добавьте дату и время с первым днем, всегда 1, а также с указанием года и месяца, там есть свойство дня недели.
Затем отсюда вы можете использовать количество дней в месяце DateTime.DaysInMonth
, чтобы определить, сколько недель вы делите на семь, а затем добавить количество дней от 1, на которое выпадает ваш первый день. Например,
public static int RowsForMonth(int month, int year)
{
DateTime first = new DateTime(year, month, 1);
//number of days pushed beyond monday this one sits
int offset = ((int)first.DayOfWeek) - 1;
int actualdays = DateTime.DaysInMonth(month, year) + offset;
decimal rows = (actualdays / 7);
if ((rows - ((int)rows)) > .1)
{
rows++;
}
return rows;
}