DateTime.ToLocalTime() in winter/summer time

13,782

Solution 1

http://msdn.microsoft.com/en-us/library/system.datetime.tolocaltime.aspx

On Windows XP systems, the ToLocalTime method recognizes only the current adjustment rule when converting from UTC to local time. As a result, conversions for periods before the current adjustment rule came into effect may not accurately reflect the difference between UTC and local time.

So you will have to find another way to figure it out.

Solution 2

My guess is that the time zone data on your system may be out of date - or it's due to the limitation jsobo mentioned.

One option you might want to (cautiously) pursue is using my date/time API, Noda Time. This has conversion to/from DateTime so you could use DateTime elsewhere in your code, although obviously I believe your code would be clearer if you used Noda Time throughout :)

Noda Time isn't "v1.0-ready" yet, but mostly because of a few missing features. Whether you're willing to take the risk of a non-v1.0 open source project or not is up to you, of course, but I'd be very happy to help with any issues you run into. (I'm really trying to find real-life use cases, so if there are any missing features you need, I may well be able to implement them in anticipation of others needing the same thing.)

Noda Time uses the zoneinfo time zone database, not the one built into Windows, so it shouldn't have the same issues.

To check, you'd use code like this:

DateTimeZone belgradeZone = DateTimeZone.ForId("Europe/Belgrade"); // Or whatever
// Alternatively...
DateTimeZone localZone = DateTimeZone.SystemDefault;
ZonedDateTime utc = new ZonedDateTime(2011, 10, 23, 9, 0, 0, DateTimeZone.Utc);
ZonedDateTime belgrade = new ZonedDateTime(utc.ToInstant(), belgradeZone);
Console.WriteLine(belgrade.LocalDateTime);

Solution 3

I use the same time zone, and when I try it I get the correct values:

var utcDate1 = new DateTime(2011, 10, 23, 9, 0, 0, DateTimeKind.Utc);
Console.WriteLine(utcDate1);
Console.WriteLine(utcDate1.ToLocalTime());

var utcDate2 = new DateTime(2011, 11, 2, 9, 0, 0, DateTimeKind.Utc);
Console.WriteLine(utcDate2);
Console.WriteLine(utcDate2.ToLocalTime());

Output:

2011-10-23 09:00:00
2011-10-23 11:00:00
2011-11-02 09:00:00
2011-11-02 10:00:00
Share:
13,782
Tom
Author by

Tom

Updated on September 15, 2022

Comments

  • Tom
    Tom over 1 year

    I am using DateTime.ToLocalTime() to convert dates from UTC to local time. My time zone is GMT+1(Belgrade, Budapest, Lubjna...), it is set properly in Windows Settings (XP).

    Last weekend in our time zone we changed to winter time to summer time, it means, we set back local time by one hour.

    As I see ToLocalTime method behaves strange from that moment. When I use it to convert dates that are after this winter time change, it works great, like this:

    var utcDate2 = new DateTime(2011, 11, 2, 9, 0, 0,DateTimeKind.Utc);
    

    utcDate1.ToLocalTime() value is: 2011.11.02. 10:00:00 it is correct

    Burt when I want to convert a date before this change (e.g. a date from summer time) it gives back a bad value like this:

    var utcDate1 = new DateTime(2011, 10, 23, 9, 0, 0,DateTimeKind.Utc);
    

    utcDate2.ToLocalTime() value is: 2011.10.23. 10:00:00 it is incorrect It should be 2011.10.23. 11:00:00

    What should I do to get correct values? How should I use ToLocalTime that also adjust winter/summer time?

  • Tom
    Tom over 12 years
    It is a very sad news for me :(
  • Jon Skeet
    Jon Skeet over 12 years
    On the other hand, I'd expect 2011 to reflect the current adjustment rule - this should be a problem for historical data, not the current year.
  • Tom
    Tom over 12 years
    As my example shows, it is a problem for the current year also
  • Guffa
    Guffa over 12 years
    Do you mean that the adjustment rule has changed since the adjustment happened three days ago? Otherwise it is the current adjustment rule that is used.
  • Tom
    Tom over 12 years
    3 days ago there was the summer time/winter time change in my time zone. If I convert now 'a date to local time that is in summer time' it gives back an incorrect value
  • Jon Skeet
    Jon Skeet over 12 years
    Which operating system are you using? This may well be XP-specific.
  • Guffa
    Guffa over 12 years
    Sorry that I didn't mention that. I am using Windows 7.
  • Tom
    Tom over 12 years
    Thanks. Does it use a local database or some on the internet?
  • Philipp M
    Philipp M over 9 years
    @Tom see here for information about the database.