C# 为什么 DateTime.Parse 不能解析 UTC 日期
声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow
原文地址: http://stackoverflow.com/questions/1756639/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me):
StackOverFlow
Why can't DateTime.Parse parse UTC date
提问by Dve
Whycan't it parse this:
为什么它不能解析这个:
DateTime.Parse("Tue, 1 Jan 2008 00:00:00 UTC")
采纳答案by Simon P Stevens
It can't parse that string because "UTC" is not a valid time zone designator.
它无法解析该字符串,因为“UTC”不是有效的时区指示符。
UTC time is denoted by adding a 'Z' to the end of the time string, so your parsing code should look like this:
UTC 时间通过在时间字符串的末尾添加一个“Z”来表示,因此您的解析代码应如下所示:
DateTime.Parse("Tue, 1 Jan 2008 00:00:00Z");
From the Wikipedia article on ISO 8601
If the time is in UTC, add a 'Z' directly after the time without a space. 'Z' is the zone designator for the zero UTC offset. "09:30 UTC" is therefore represented as "09:30Z" or "0930Z". "14:45:15 UTC" would be "14:45:15Z" or "144515Z".
UTC time is also known as 'Zulu' time, since 'Zulu' is the NATO phonetic alphabet word for 'Z'.
如果时间是 UTC,请在时间后直接添加一个“Z”,不要有空格。'Z' 是零 UTC 偏移的区域指示符。因此,“09:30 UTC”表示为“09:30Z”或“0930Z”。“14:45:15 UTC”将是“14:45:15Z”或“144515Z”。
UTC 时间也称为“祖鲁语”时间,因为“祖鲁语”是“Z”的北约拼音字母词。
回答by Ian P
Not sure why, but you can wrap DateTime.ToUniversalTime in a try / catch and achieve the same result in more code.
不知道为什么,但是您可以在 try / catch 中包装 DateTime.ToUniversalTime 并在更多代码中实现相同的结果。
Good luck.
祝你好运。
回答by Darin Dimitrov
You need to specify the format:
您需要指定格式:
DateTime date = DateTime.ParseExact(
"Tue, 1 Jan 2008 00:00:00 UTC",
"ddd, d MMM yyyy HH:mm:ss UTC",
CultureInfo.InvariantCulture);
回答by user213809
or use the AdjustToUniversal DateTimeStyle in a call to
或在调用中使用 AdjustToUniversal DateTimeStyle
DateTime.ParseExact(String, String[], IFormatProvider, DateTimeStyles)
回答by HackerBaloo
It's not a valid format, however "Tue, 1 Jan 2008 00:00:00 GMT" is.
这不是一个有效的格式,但是“2008 年 1 月 1 日星期二 00:00:00 GMT”是。
The documentation says like this:
文档是这样说的:
A string that includes time zone information and conforms to ISO 8601. For example, the first of the following two strings designates the Coordinated Universal Time (UTC); the second designates the time in a time zone seven hours earlier than UTC:
包含时区信息并符合 ISO 8601 的字符串。例如,以下两个字符串中的第一个指定协调世界时 (UTC);第二个指定比 UTC 早 7 小时的时区时间:
2008-11-01T19:35:00.0000000Z
2008-11-01T19:35:00.0000000Z
A string that includes the GMT designator and conforms to the RFC 1123 time format. For example:
包含 GMT 指示符并符合 RFC 1123 时间格式的字符串。例如:
Sat, 01 Nov 2008 19:35:00 GMT
2008 年 11 月 1 日星期六 19:35:00 GMT
A string that includes the date and time along with time zone offset information. For example:
包含日期和时间以及时区偏移信息的字符串。例如:
03/01/2009 05:42:00 -5:00
03/01/2009 05:42:00 -5:00
回答by satbot
To correctly parse the string given in the question without changing it, use the following:
要正确解析问题中给出的字符串而不更改它,请使用以下命令:
using System.Globalization;
string dateString = "Tue, 1 Jan 2008 00:00:00 UTC";
DateTime parsedDate = DateTime.ParseExact(dateString, "ddd, d MMM yyyy hh:mm:ss UTC", CultureInfo.CurrentCulture, DateTimeStyles.AssumeUniversal);
This implementation uses a string to specify the exact format of the date string that is being parsed. The DateTimeStyles parameter is used to specify that the given string is a coordinated universal time string.
此实现使用字符串来指定正在解析的日期字符串的确切格式。DateTimeStyles 参数用于指定给定的字符串是协调的通用时间字符串。
回答by David Thielen
Assuming you use the format "o" for your datetime so you have "2016-07-24T18:47:36Z", there is a very simple way to handle this.
假设您的日期时间使用格式“o”,因此您有“2016-07-24T18:47:36Z”,有一个非常简单的方法来处理这个问题。
Call DateTime.Parse("2016-07-24T18:47:36Z").ToUniversalTime()
.
打电话DateTime.Parse("2016-07-24T18:47:36Z").ToUniversalTime()
。
What happens when you call DateTime.Parse("2016-07-24T18:47:36Z")
is you get a DateTime
set to the local timezone. So it converts it to the local time.
当你打电话时会发生什么,你DateTime.Parse("2016-07-24T18:47:36Z")
会得到一个DateTime
本地时区的设置。所以它将其转换为当地时间。
The ToUniversalTime()
changes it to a UTC DateTime
and converts it back to UTC time.
将其ToUniversalTime()
更改为 UTCDateTime
并将其转换回 UTC 时间。
回答by Ricardo de Assuncao Goncalves
Just use that:
只需使用它:
var myDateUtc = DateTime.SpecifyKind(DateTime.Parse("Tue, 1 Jan 2008 00:00:00"), DateTimeKind.Utc);
if (myDateUtc.Kind == DateTimeKind.Utc)
{
Console.WriteLine("Yes. I am UTC!");
}
You can test this code using the online c# compiler:
您可以使用在线 c# 编译器测试此代码:
I hope it helps.
我希望它有帮助。
回答by Mike Godin
Just replace "UTC" with "GMT" -- simple and doesn't break correctly formatted dates:
只需将“UTC”替换为“GMT”——简单且不会破坏格式正确的日期:
DateTime.Parse("Tue, 1 Jan 2008 00:00:00 UTC".Replace("UTC", "GMT"))
回答by XDS
I've put together a utility method which employs all tips shown here plus some more:
我整理了一个实用方法,它采用了此处显示的所有技巧以及更多技巧:
static private readonly string[] MostCommonDateStringFormatsFromWeb = {
"yyyy'-'MM'-'dd'T'hh:mm:ssZ", // momentjs aka universal sortable with 'T' 2008-04-10T06:30:00Z this is default format employed by moment().utc().format()
"yyyy'-'MM'-'dd'T'hh:mm:ss.fffZ", // syncfusion 2008-04-10T06:30:00.000Z retarded string format for dates that syncfusion libs churn out when invoked by ejgrid for odata filtering and so on
"O", // iso8601 2008-04-10T06:30:00.0000000
"s", // sortable 2008-04-10T06:30:00
"u" // universal sortable 2008-04-10 06:30:00Z
};
static public bool TryParseWebDateStringExactToUTC(
out DateTime date,
string input,
string[] formats = null,
DateTimeStyles? styles = null,
IFormatProvider formatProvider = null
)
{
formats = formats ?? MostCommonDateStringFormatsFromWeb;
return TryParseDateStringExactToUTC(out date, input, formats, styles, formatProvider);
}
static public bool TryParseDateStringExactToUTC(
out DateTime date,
string input,
string[] formats = null,
DateTimeStyles? styles = null,
IFormatProvider formatProvider = null
)
{
styles = styles ?? DateTimeStyles.AllowWhiteSpaces | DateTimeStyles.AssumeUniversal | DateTimeStyles.AdjustToUniversal; //0 utc
formatProvider = formatProvider ?? CultureInfo.InvariantCulture;
var verdict = DateTime.TryParseExact(input, result: out date, style: styles.Value, formats: formats, provider: formatProvider);
if (verdict && date.Kind == DateTimeKind.Local) //1
{
date = date.ToUniversalTime();
}
return verdict;
//0 employing adjusttouniversal is vital in order for the resulting date to be in utc when the 'Z' flag is employed at the end of the input string
// like for instance in 2008-04-10T06:30.000Z
//1 local should never happen with the default settings but it can happen when settings get overriden we want to forcibly return utc though
}
Notice the use of '-' and 'T' (single-quoted). This is done as a matter of best practice since regional settings interfere with the interpretation of chars such as '-' causing it to be interpreted as '/' or '.' or whatever your regional settings denote as date-components-separator. I have also included a second utility method which show-cases how to parse most commonly seen date-string formats fed to rest-api backends from web clients. Enjoy.
请注意“-”和“T”(单引号)的使用。这是作为最佳实践完成的,因为区域设置会干扰诸如“-”之类的字符的解释,导致其被解释为“/”或“。”。或任何您的区域设置表示为日期组件分隔符。我还包含了第二个实用程序方法,它展示了如何解析从 Web 客户端提供给 rest-api 后端的最常见日期字符串格式。享受。