【问题标题】:C# DateTime conversion when time changes from winter to summer time当时间从冬季时间变为夏季时间时,C# DateTime 转换
【发布时间】:2021-03-27 08:39:22
【问题描述】:

我收到此错误:

提供的 DateTime 表示无效时间。例如,当 时钟向前调整,在被跳过的时间段内的任何时间 无效

当我尝试将时间 2020-03-29 02:30 从东欧时间 (GMT+2) 转换为 UTC 时间时。

根据this site,芬兰的时钟应该在 03:00 发生变化,这意味着时间 02:30 应该可以转换为 UTC。

但是当我运行下面的代码时,抛出了一个异常。

var timezoneMap = TimeZoneInfo.GetSystemTimeZones().ToDictionary(x => x.Id, x => x);
var timezoneInfo = timezoneMap["E. Europe Standard Time"]; 

var localTime1 = DateTime.SpecifyKind(new DateTime(2020, 12, 15, 0, 0, 0), DateTimeKind.Unspecified);
var localTime2 = DateTime.SpecifyKind(new DateTime(2020, 3, 29, 2, 30, 0), DateTimeKind.Unspecified);

var utc1 = TimeZoneInfo.ConvertTimeToUtc(localTime1, timezoneInfo); // 2020-12-14 22:00 correct
var utc2 = TimeZoneInfo.ConvertTimeToUtc(localTime2, timezoneInfo); // throws exception

第二次转换有什么问题,为什么会出现异常?

【问题讨论】:

标签: c#


【解决方案1】:

您正在查看的网站使用IANA time zone data,我认为它是准确的。

但是您的代码使用 Windows 时区数据库,在这种情况下,它看起来存在差异......它似乎认为转换是在 UTC 午夜而不是 UTC 凌晨 1 点。下面的代码可以证明这一点:

using System;
using System.Globalization;

class Program
{
    static void Main()
    {
        var zone = TimeZoneInfo.FindSystemTimeZoneById("E. Europe Standard Time");

        // Start at 2020-03-28T23:00Z - definitely before the transition
        var utc = new DateTime(2020, 3, 28, 23, 0, 0, DateTimeKind.Utc);
        for (int i = 0; i < 8; i++)
        {
            var local = TimeZoneInfo.ConvertTime(utc, zone);
            Console.WriteLine($"{utc:yyyy-MM-dd HH:mm} UTC => {local:yyyy-MM-dd HH:mm} local");
            utc = utc.AddMinutes(30);
        }
    }
}

输出(带注释):

2020-03-28 23:00 UTC => 2020-03-29 01:00 local
2020-03-28 23:30 UTC => 2020-03-29 01:30 local
2020-03-29 00:00 UTC => 2020-03-29 03:00 local  <= Note the change here, at midnight UTC
2020-03-29 00:30 UTC => 2020-03-29 03:30 local
2020-03-29 01:00 UTC => 2020-03-29 04:00 local
2020-03-29 01:30 UTC => 2020-03-29 04:30 local
2020-03-29 02:00 UTC => 2020-03-29 05:00 local
2020-03-29 02:30 UTC => 2020-03-29 05:30 local

当前的 IANA 数据确实确实表示 UTC 时间凌晨 1 点,如 this line of the rules 所示。所以我相信网站正确地解释了数据,这只是 Windows 时区数据库“不同”的问题(而且,我怀疑是不正确的)。

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 2016-11-07
    • 1970-01-01
    • 2019-06-18
    • 2023-01-29
    • 2020-11-26
    • 1970-01-01
    • 2020-02-20
    相关资源
    最近更新 更多