4

While trying to get the number of weeks in a year I tried this:

maxWeek = calendar.GetWeekOfYear(New Date(t_year, 12, 31), 
          CalendarWeekRule.FirstFourDayWeek, DayOfWeek.Monday)

Which didn't work well for my purpouse, but I noticed something weird. For 2014-12-31 it returned 53 and for 2015-01-01 it returned 1. For 2015-01-05 it returned 2. That means that the weeks 53 and 1 are smaller then 7 days!

I need the result to be ISO Week compliant. I couldn't find online any examples of calendars following this same logic. Them all show the week 1 as from 2014-12-29 to 2015-01-04.

Ňɏssa Pøngjǣrdenlarp
  • 38,411
  • 12
  • 59
  • 178
mathiasfk
  • 1,278
  • 1
  • 19
  • 38
  • 2
    You are asking for `CalendarWeekRule.FirstFourDayWeek`. If you don't like the result, try the [other options](http://msdn.microsoft.com/en-us/library/system.globalization.calendarweekrule.aspx). – GSerg Jan 02 '15 at 16:12
  • @GSerg Indeed I tried This other rules, but any returned 01 from the 29th of december, as I would expect [ISO week](http://en.wikipedia.org/wiki/ISO_week_date). By what I see on the examples on this msdn page there is no rule compatible with what I want. – mathiasfk Jan 02 '15 at 16:36

2 Answers2

7

Your original post does not mention you are looking for ISO week, which may have made what you want unclear.

The NET GetWeekOfYear using FirstFourDayWeek and DayOfWeek.Monday is almost like an ISO Week. The difference is that an ISO Week is always seven days. Keep in mind that an ISO Date is not just a different format, but a different calendar complete with its own terms (like leap week). Your default NET calandar on the other hand is Gregorian.

It is not hard to tweak a NET WOY to an ISO Week:

Public Shared Function GetISOWeekOfYear(dt As DateTime) As Integer
    Dim cal As Calendar = CultureInfo.InvariantCulture.Calendar
    Dim d As DayOfWeek = cal.GetDayOfWeek(dt)

    If (d >= DayOfWeek.Monday) AndAlso (d <= DayOfWeek.Wednesday) Then
        dt = dt.AddDays(3)
    End If

    Return cal.GetWeekOfYear(dt, CalendarWeekRule.FirstFourDayWeek, DayOfWeek.Monday)

End Function

Simple tester for 12/31/xxxx:

For n As Integer = 1990 To 2016
    Console.WriteLine("{0}: week:{1}", n.ToString,
                      GetISOWeekOfYear(New DateTime(n, 12, 31)).ToString)
Next

Output of just the last few:

2005: week:52
2006: week:52
2007: week:1
2008: week:1
2009: week:53
2010: week:52
2011: week:52
2012: week:1
2013: week:1
2014: week:1
2015: week:53
2016: week:52

Ňɏssa Pøngjǣrdenlarp
  • 38,411
  • 12
  • 59
  • 178
  • Thanks, this seems to work! You are right, I should have mentioned in the post that I was looking for the ISO week. – mathiasfk Jan 06 '15 at 15:56
  • Unbelievable how crazy it is just to get a week number thats ISO compliant. Thanks for this. – DreamTeK May 17 '16 at 15:36
0

Try this:

Dim maxWeek As Integer = Globalization.ISOWeek.GetWeekOfYear(New Date(t_year, 12, 31))

Applies to .NET versions: .NET 5, .NET 6, .NET Core 3.0, .NET Core 3.1 and .NET Standard 2.1

Get Details here: https://learn.microsoft.com/en-us/dotnet/api/system.globalization.isoweek.getweekofyear?view=net-6.0

AreMoh
  • 1
  • 2