如何以UTC格式打印DateTime?
Posted
tags:
篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了如何以UTC格式打印DateTime?相关的知识,希望对你有一定的参考价值。
我只是尝试以UTC等效时间格式打印DateTime。我究竟做错了什么?
var utcEpoch = DateTime.Parse("1970-01-01", CultureInfo.InvariantCulture, DateTimeStyles.AssumeUniversal); //This specifies the time I provided is in UTC
Console.WriteLine(utcEpoch.ToString("yyyy-MM-dd HH:mm:ss zzz")); //This properly shows my UTC offset of -6, so it's not wrong
Console.WriteLine(utcEpoch.ToString("u")); //This just flat out seems wrong because it doesn't specify a timezone or offset in its output
> 1969-12-31 18:00:00 -06:00
> 1969-12-31 18:00:00Z
我期望看到最后一个1970-01-01 00:00:00Z
。
我认为你误解了API正在做什么。
首先要注意的是,DateTimeStyles.AssumeUniversal
和DateTimeStyles.AssumeLocal
都将返回DateTime,其中Kind = Local
> DateTime.Parse("1970-01-01 00:00:00", CultureInfo.InvariantCulture, DateTimeStyles.AssumeUniversal).Kind
=> Local
> DateTime.Parse("1970-01-01 00:00:00", CultureInfo.InvariantCulture, DateTimeStyles.AssumeLocal).Kind
=> Local
所以无论我们将获得当地约会。这意味着API很可能是为了从UTC日期获得本地时间。如果这是正确的,我们试试吧。
我在瑞典,所以我们在标准时间内是UTC + 1。因此,如果我使用DateTimeStyles.AssumeUniversal
并放入今天的日期,我应该在今天的01:00获得当地日期。
在C#Interactive中运行:
> DateTime.Parse("2018-03-03", .CultureInfo.InvariantCulture, .DateTimeStyles.AssumeUniversal)
=> [2018-03-03 01:00:00]
意思是C#假设我输入的字符串是UTC,我希望它在本地,所以它“固定”了它。
对AssumeLocal
做同样的事情。
DateTime.Parse("2018-03-03", .CultureInfo.InvariantCulture, .DateTimeStyles.AssumeLocal)
=> [2018-03-03 00:00:00]
正如所料,我们现在将输入视为本地字符串并获得相同的值。
要获得UTC日期,您可以指定种类
DateTime.SpecifyKind(DateTime.Parse("2018-03-03", CultureInfo.InvariantCulture), DateTimeKind.Utc).ToString("o")
=> "2018-03-03T00:00:00.0000000Z"
来自The Universal Sortable ("u"
) Format Specifier:
虽然结果字符串应将时间表示为协调世界时(UTC),但在格式化操作期间不会执行原始DateTime值的转换。因此,在格式化之前,必须通过调用
DateTime.ToUniversalTime
方法将DateTime值转换为UTC。相反,DateTimeOffset值会自动执行此转换;在格式化操作之前无需调用DateTimeOffset.ToUniversalTime方法。
你的utcEpoch.Kind
不是UTC
,它是Local
。 DateTime's are triciker than you might think。你期望它会将UTC
作为Kind
财产归还,但事实并非如此。它返回Local
。
这种情况也在Phil Haack blog post上讨论过,Matt Johnson对此有一个很好的评论;
AssumeLocal
和AssumeUniversal
都与输入字符串的解释方式有关。它们本身也不会改变输出类型。默认输出类型是
Local
。要使它成为Utc
,您可以使用AdjustToUniversal
风格。
DateTimeStyles
枚举是基于标志的,因此您可以通过某些有意义的方式将它们组合在一起。要实现您最初设置的目的(将输入解析为UTC
并将其输出为UTC
),那么您将使用:DateTime utcDate = DateTime.Parse(“10/01/2006 19:30”,culture,DateTimeStyles.AssumeUniversal | DateTimeStyles.AdjustToUniversal);
正如其他人指出的那样,单独调用
ToUniversalTime()
也会起作用,但这在技术上更正确。
你也可以在referance source上看到它;
case 'u': // Universal time in sortable format.
if (offset != NullOffset)
{
// Convert to UTC invariants mean this will be in range
dateTime = dateTime - offset;
}
else if (dateTime.Kind == DateTimeKind.Local)
{
InvalidFormatForLocal(format, dateTime);
}
以上是关于如何以UTC格式打印DateTime?的主要内容,如果未能解决你的问题,请参考以下文章
在填充的数据表中将 datetime 列从 utc 转换为本地时间