Câu trả lời:
Lưu ý cho độc giả: Một số bình luận đã chỉ ra một số vấn đề trong câu trả lời này (liên quan đặc biệt đến gợi ý đầu tiên). Tham khảo phần bình luận để biết thêm thông tin.
DateTime.UtcNow.ToString("yyyy-MM-ddTHH\\:mm\\:ss.fffffffzzz");
Điều này cung cấp cho bạn một ngày tương tự như 2008-09-22T13: 57: 31.2311892-04: 00 .
Một cách khác là:
DateTime.UtcNow.ToString("o");
mang đến cho bạn 2008-09-22T14: 01: 54.9571247Z
Để có được định dạng đã chỉ định, bạn có thể sử dụng:
DateTime.UtcNow.ToString("yyyy-MM-ddTHH:mm:ssZ")
ToString("yyyy-MM-ddTHH:mm:ssK")
nó để làm việc (với plugin timeago jquery tôi đang sử dụng).
dt.ToString("s") + dt.ToString("zzz")
// 2013-12-05T07: 19: 04-08: 00
DateTime.UtcNow.ToString("s", System.Globalization.CultureInfo.InvariantCulture)
sẽ cung cấp cho bạn những gì bạn đang tìm kiếm vì trình xác định định dạng "s" được mô tả dưới dạng mẫu ngày / giờ có thể sắp xếp; phù hợp với ISO 8601.
DateTime.UtcNow.ToString(CultureInfo.InvariantCulture.DateTimeFormat.SortableDateTimePattern);
Tuy nhiên, vì tất cả các loại này đều loại trừ múi giờ, v.v., bạn có thể không có lựa chọn nào khác ngoài sử dụng định dạng rõ ràng, tức là"yyyy-MM-ddTHH:mm:ss.fffZ"
Z
trông như thế này: DateTime.UtcNow.ToString(c, CultureInfo.InvariantCulture)) => 2012-06-26T11:55:36
và không có độ phân giải mili giây nào là rất tốt để có được vì máy tính thực hiện một số lượng tích tắc mỗi giây.
o
bạn có 2012-06-26T11:55:36.1007668Z
nghĩa là 36.1007668
giây, vì vậy bạn có được độ phân giải xuống đến 1/10^7
một giây. Từ ISO8601: 2004If a decimal fraction is included, lower order time elements (if any) shall be omitted and the decimal fraction shall be divided from the integer part by the decimal sign [...] the comma (,) or full stop (.)
"s"
không có ý nghĩa gì bởi vì: "O" (hoặc "o"), "R" (hoặc "r"), "s" và "u". Các chuỗi này tương ứng với các chuỗi định dạng tùy chỉnh được xác định bởi văn hóa bất biến. Họ tạo ra các biểu diễn chuỗi của các giá trị ngày và thời gian được dự định là giống hệt nhau giữa các nền văn hóa.
DateTime.Now.ToString("s", new CultureInfo(myCulture))
.
DateTime.UtcNow.ToString("s")
Trả về một cái gì đó như 2008-04-10T06: 30: 00
UtcNow
rõ ràng trả về thời gian UTC vì vậy không có hại trong:
string.Concat(DateTime.UtcNow.ToString("s"), "Z")
a + b
biên dịch thành mã trung gian giống như string.Concat(a, b)
(tất nhiên giả sử rằng a và b là các chuỗi) vì vậy không có sự khác biệt về hiệu suất hoặc mức tiêu thụ bộ nhớ.
Sử dụng:
private void TimeFormats()
{
DateTime localTime = DateTime.Now;
DateTime utcTime = DateTime.UtcNow;
DateTimeOffset localTimeAndOffset = new DateTimeOffset(localTime, TimeZoneInfo.Local.GetUtcOffset(localTime));
//UTC
string strUtcTime_o = utcTime.ToString("o");
string strUtcTime_s = utcTime.ToString("s");
string strUtcTime_custom = utcTime.ToString("yyyy-MM-ddTHH:mm:ssK");
//Local
string strLocalTimeAndOffset_o = localTimeAndOffset.ToString("o");
string strLocalTimeAndOffset_s = localTimeAndOffset.ToString("s");
string strLocalTimeAndOffset_custom = utcTime.ToString("yyyy-MM-ddTHH:mm:ssK");
//Output
Response.Write("<br/>UTC<br/>");
Response.Write("strUtcTime_o: " + strUtcTime_o + "<br/>");
Response.Write("strUtcTime_s: " + strUtcTime_s + "<br/>");
Response.Write("strUtcTime_custom: " + strUtcTime_custom + "<br/>");
Response.Write("<br/>Local Time<br/>");
Response.Write("strLocalTimeAndOffset_o: " + strLocalTimeAndOffset_o + "<br/>");
Response.Write("strLocalTimeAndOffset_s: " + strLocalTimeAndOffset_s + "<br/>");
Response.Write("strLocalTimeAndOffset_custom: " + strLocalTimeAndOffset_custom + "<br/>");
}
UTC
strUtcTime_o: 2012-09-17T22:02:51.4021600Z
strUtcTime_s: 2012-09-17T22:02:51
strUtcTime_custom: 2012-09-17T22:02:51Z
Local Time
strLocalTimeAndOffset_o: 2012-09-17T15:02:51.4021600-07:00
strLocalTimeAndOffset_s: 2012-09-17T15:02:51
strLocalTimeAndOffset_custom: 2012-09-17T22:02:51Z
string strLocalTimeAndOffset_custom = localTimeAndOffset.ToString("yyyy-MM-ddTHH:mm:ssK");
sẽ dẫn đến:strLocalTimeAndOffset_custom: 2012-09-17T22:02:51-07:00
o
là định dạng ISO-8601.
System.DateTime.UtcNow.ToString("o")
=>
val it : string = "2013-10-13T13:03:50.2950037Z"
Bạn có thể lấy "Z" ( ISO 8601 UTC ) với mã tiếp theo:
Dim tmpDate As DateTime = New DateTime(Now.Ticks, DateTimeKind.Utc)
Dim res as String = tmpDate.toString("o") '2009-06-15T13:45:30.0000000Z
Đây là lý do tại sao:
ISO 8601 có một số định dạng khác nhau:
DateTimeKind. Tiêu điểm
2009-06-15T13:45:30.0000000-07:00
DateTimeKind.Utc
2009-06-15T13:45:30.0000000Z
DateTimeKind.Unspecified
2009-06-15T13:45:30.0000000
.NET cung cấp cho chúng ta một enum với các tùy chọn đó:
'2009-06-15T13:45:30.0000000-07:00
Dim strTmp1 As String = New DateTime(Now.Ticks, DateTimeKind.Local).ToString("o")
'2009-06-15T13:45:30.0000000Z
Dim strTmp2 As String = New DateTime(Now.Ticks, DateTimeKind.Utc).ToString("o")
'2009-06-15T13:45:30.0000000
Dim strTmp3 As String = New DateTime(Now.Ticks, DateTimeKind.Unspecified).ToString("o")
Lưu ý : Nếu bạn áp dụng "tiện ích đồng hồ" của Visual Studio 2008 cho phần toString ("o"), bạn có thể nhận được các kết quả khác nhau, tôi không biết đó có phải là lỗi không, nhưng trong trường hợp này bạn có kết quả tốt hơn khi sử dụng biến Chuỗi nếu bạn đang gỡ lỗi.
Nguồn: Chuỗi định dạng ngày và giờ chuẩn (MSDN)
Nếu bạn phải sử dụng DateTime đến ISO 8601, thì ToString ("o") sẽ mang lại những gì bạn đang tìm kiếm. Ví dụ,
2015-07-06T12:08:27
Tuy nhiên, DateTime + TimeZone có thể trình bày các vấn đề khác như được mô tả trong bài đăng trên blog DateTime và DateTime Offerset trong .NET: Thực tiễn tốt và những cạm bẫy phổ biến :
DateTime có vô số bẫy trong đó được thiết kế để cung cấp cho các lỗi mã của bạn:
1.- Giá trị DateTime với DateTimeKind.Unspecified là tin xấu.
2.- DateTime không quan tâm đến UTC / Local khi so sánh.
3.- Giá trị DateTime không biết chuỗi định dạng chuẩn.
4.- Phân tích một chuỗi có điểm đánh dấu UTC bằng DateTime không đảm bảo thời gian UTC.
Ngạc nhiên vì không ai đề nghị nó:
System.DateTime.UtcNow.ToString("u").Replace(' ','T')
# Using PowerShell Core to demo
# Lowercase "u" format
[System.DateTime]::UtcNow.ToString("u")
> 2020-02-06 01:00:32Z
# Lowercase "u" format with replacement
[System.DateTime]::UtcNow.ToString("u").Replace(' ','T')
> 2020-02-06T01:00:32Z
Các UniversalSortableDateTimePattern giúp bạn gần như tất cả các cách để những gì bạn muốn (đó là hơn một RFC 3339 đại diện).
Đã thêm: Tôi đã quyết định sử dụng các điểm chuẩn trong câu trả lời https://stackoverflow.com/a/43793679/653058 để so sánh cách thức này thực hiện.
tl: dr; nó ở mức đắt đỏ nhưng vẫn chỉ hơn nửa phần nghìn giây trên chiếc máy tính xách tay cũ kỹ của tôi :-)
Thực hiện:
[Benchmark]
public string ReplaceU()
{
var text = dateTime.ToUniversalTime().ToString("u").Replace(' ', 'T');
return text;
}
Các kết quả:
// * Summary *
BenchmarkDotNet=v0.11.5, OS=Windows 10.0.19002
Intel Xeon CPU E3-1245 v3 3.40GHz, 1 CPU, 8 logical and 4 physical cores
.NET Core SDK=3.0.100
[Host] : .NET Core 3.0.0 (CoreCLR 4.700.19.46205, CoreFX 4.700.19.46214), 64bit RyuJIT
DefaultJob : .NET Core 3.0.0 (CoreCLR 4.700.19.46205, CoreFX 4.700.19.46214), 64bit RyuJIT
| Method | Mean | Error | StdDev |
|--------------------- |---------:|----------:|----------:|
| CustomDev1 | 562.4 ns | 11.135 ns | 10.936 ns |
| CustomDev2 | 525.3 ns | 3.322 ns | 3.107 ns |
| CustomDev2WithMS | 609.9 ns | 9.427 ns | 8.356 ns |
| FormatO | 356.6 ns | 6.008 ns | 5.620 ns |
| FormatS | 589.3 ns | 7.012 ns | 6.216 ns |
| FormatS_Verify | 599.8 ns | 12.054 ns | 11.275 ns |
| CustomFormatK | 549.3 ns | 4.911 ns | 4.594 ns |
| CustomFormatK_Verify | 539.9 ns | 2.917 ns | 2.436 ns |
| ReplaceU | 615.5 ns | 12.313 ns | 11.517 ns |
// * Hints *
Outliers
BenchmarkDateTimeFormat.CustomDev2WithMS: Default -> 1 outlier was removed (668.16 ns)
BenchmarkDateTimeFormat.FormatS: Default -> 1 outlier was removed (621.28 ns)
BenchmarkDateTimeFormat.CustomFormatK: Default -> 1 outlier was detected (542.55 ns)
BenchmarkDateTimeFormat.CustomFormatK_Verify: Default -> 2 outliers were removed (557.07 ns, 560.95 ns)
// * Legends *
Mean : Arithmetic mean of all measurements
Error : Half of 99.9% confidence interval
StdDev : Standard deviation of all measurements
1 ns : 1 Nanosecond (0.000000001 sec)
// ***** BenchmarkRunner: End *****
Tôi sẽ chỉ sử dụng XmlConvert
:
XmlConvert.ToString(DateTime.UtcNow, XmlDateTimeSerializationMode.RoundtripKind);
Nó sẽ tự động bảo tồn múi giờ.
Hầu hết các câu trả lời này có mili giây / micro giây mà rõ ràng không được ISO 8601 hỗ trợ. Câu trả lời đúng sẽ là:
System.DateTime.Now.ToString("yyyy-MM-ddTHH:mm:ssK");
// or
System.DateTime.Now.ToUniversalTime().ToString("yyyy-MM-ddTHH:mm:ssK");
Người giới thiệu:
DateTime.Now.ToString("yyyy-MM-dd'T'HH:mm:ss zzz");
DateTime.Now.ToString("O");
LƯU Ý: Tùy thuộc vào chuyển đổi bạn đang thực hiện, bạn sẽ sử dụng dòng đầu tiên (giống như nó) hoặc dòng thứ hai.
Đảm bảo chỉ áp dụng định dạng vào giờ địa phương, vì "zzz" là thông tin múi giờ cho chuyển đổi UTC.
Trình
"s"
xác định định dạng chuẩn biểu thị chuỗi định dạng ngày và giờ tùy chỉnh được xác định bởi thuộc tính DateTimeFormatInfo.SortableDateTimePotype . Mẫu phản ánh một tiêu chuẩn được xác định ( ISO 8601 ) và thuộc tính là chỉ đọc. Do đó, nó luôn giống nhau, bất kể văn hóa được sử dụng hoặc nhà cung cấp định dạng được cung cấp. Chuỗi định dạng tùy chỉnh là"yyyy'-'MM'-'dd'T'HH':'mm':'ss"
.Khi trình xác định định dạng chuẩn này được sử dụng, hoạt động định dạng hoặc phân tích cú pháp luôn sử dụng văn hóa bất biến.
- từ MSDN
.ToString("s")
không?
Để chuyển đổi DateTime.UtcNow thành biểu diễn chuỗi của yyyy-MM-ddTHH: mm: ssZ , bạn có thể sử dụng phương thức ToString () của cấu trúc DateTime với chuỗi định dạng tùy chỉnh. Khi sử dụng các chuỗi định dạng tùy chỉnh với DateTime, điều quan trọng cần nhớ là bạn cần thoát khỏi các phần tách biệt của mình bằng các dấu ngoặc đơn.
Sau đây sẽ trả về chuỗi phản hồi bạn muốn:
DateTime.UtcNow.ToString("yyyy'-'MM'-'dd'T'HH':'mm':'ss'Z'", DateTimeFormatInfo.InvariantInfo)
Điều thú vị là định dạng tùy chỉnh "yyyy-MM-ddTHH: mm: ssK" (không có ms) là phương thức định dạng nhanh nhất.
Ngoài ra, điều thú vị là định dạng "S" chậm trên Classic và nhanh trên Core ...
Tất nhiên các số rất gần nhau, giữa một số hàng khác nhau là không đáng kể (các thử nghiệm có hậu tố _Verify
giống như các số không có hậu tố đó, chứng tỏ độ lặp lại kết quả)
BenchmarkDotNet=v0.10.5, OS=Windows 10.0.14393
Processor=Intel Core i5-2500K CPU 3.30GHz (Sandy Bridge), ProcessorCount=4
Frequency=3233539 Hz, Resolution=309.2587 ns, Timer=TSC
[Host] : Clr 4.0.30319.42000, 64bit RyuJIT-v4.6.1637.0
Clr : Clr 4.0.30319.42000, 64bit RyuJIT-v4.6.1637.0
Core : .NET Core 4.6.25009.03, 64bit RyuJIT
Method | Job | Runtime | Mean | Error | StdDev | Median | Min | Max | Rank | Gen 0 | Allocated |
--------------------- |----- |-------- |-----------:|----------:|----------:|-----------:|-----------:|-----------:|-----:|-------:|----------:|
CustomDev1 | Clr | Clr | 1,089.0 ns | 22.179 ns | 20.746 ns | 1,079.9 ns | 1,068.9 ns | 1,133.2 ns | 8 | 0.1086 | 424 B |
CustomDev2 | Clr | Clr | 1,032.3 ns | 19.897 ns | 21.289 ns | 1,024.7 ns | 1,000.3 ns | 1,072.0 ns | 7 | 0.1165 | 424 B |
CustomDev2WithMS | Clr | Clr | 1,168.2 ns | 16.543 ns | 15.474 ns | 1,168.5 ns | 1,149.3 ns | 1,189.2 ns | 10 | 0.1625 | 592 B |
FormatO | Clr | Clr | 1,563.7 ns | 31.244 ns | 54.721 ns | 1,532.5 ns | 1,497.8 ns | 1,703.5 ns | 14 | 0.2897 | 976 B |
FormatS | Clr | Clr | 1,243.5 ns | 24.615 ns | 31.130 ns | 1,229.3 ns | 1,200.6 ns | 1,324.2 ns | 13 | 0.2865 | 984 B |
FormatS_Verify | Clr | Clr | 1,217.6 ns | 11.486 ns | 10.744 ns | 1,216.2 ns | 1,205.5 ns | 1,244.3 ns | 12 | 0.2885 | 984 B |
CustomFormatK | Clr | Clr | 912.2 ns | 17.915 ns | 18.398 ns | 916.6 ns | 878.3 ns | 934.1 ns | 4 | 0.0629 | 240 B |
CustomFormatK_Verify | Clr | Clr | 894.0 ns | 3.877 ns | 3.626 ns | 893.8 ns | 885.1 ns | 900.0 ns | 3 | 0.0636 | 240 B |
CustomDev1 | Core | Core | 989.1 ns | 12.550 ns | 11.739 ns | 983.8 ns | 976.8 ns | 1,015.5 ns | 6 | 0.1101 | 423 B |
CustomDev2 | Core | Core | 964.3 ns | 18.826 ns | 23.809 ns | 954.1 ns | 935.5 ns | 1,015.6 ns | 5 | 0.1267 | 423 B |
CustomDev2WithMS | Core | Core | 1,136.0 ns | 21.914 ns | 27.714 ns | 1,138.1 ns | 1,099.9 ns | 1,200.2 ns | 9 | 0.1752 | 590 B |
FormatO | Core | Core | 1,201.5 ns | 16.262 ns | 15.211 ns | 1,202.3 ns | 1,178.2 ns | 1,225.5 ns | 11 | 0.0656 | 271 B |
FormatS | Core | Core | 993.5 ns | 19.272 ns | 24.372 ns | 999.4 ns | 954.2 ns | 1,029.5 ns | 6 | 0.0633 | 279 B |
FormatS_Verify | Core | Core | 1,003.1 ns | 17.577 ns | 16.442 ns | 1,009.2 ns | 976.1 ns | 1,024.3 ns | 6 | 0.0674 | 279 B |
CustomFormatK | Core | Core | 878.2 ns | 17.017 ns | 20.898 ns | 877.7 ns | 851.4 ns | 928.1 ns | 2 | 0.0555 | 215 B |
CustomFormatK_Verify | Core | Core | 863.6 ns | 3.968 ns | 3.712 ns | 863.0 ns | 858.6 ns | 870.8 ns | 1 | 0.0550 | 215 B |
Mã số:
public class BenchmarkDateTimeFormat
{
public static DateTime dateTime = DateTime.Now;
[Benchmark]
public string CustomDev1()
{
var d = dateTime.ToUniversalTime();
var sb = new StringBuilder(20);
sb.Append(d.Year).Append("-");
if (d.Month <= 9)
sb.Append("0");
sb.Append(d.Month).Append("-");
if (d.Day <= 9)
sb.Append("0");
sb.Append(d.Day).Append("T");
if (d.Hour <= 9)
sb.Append("0");
sb.Append(d.Hour).Append(":");
if (d.Minute <= 9)
sb.Append("0");
sb.Append(d.Minute).Append(":");
if (d.Second <= 9)
sb.Append("0");
sb.Append(d.Second).Append("Z");
var text = sb.ToString();
return text;
}
[Benchmark]
public string CustomDev2()
{
var u = dateTime.ToUniversalTime();
var sb = new StringBuilder(20);
var y = u.Year;
var d = u.Day;
var M = u.Month;
var h = u.Hour;
var m = u.Minute;
var s = u.Second;
sb.Append(y).Append("-");
if (M <= 9)
sb.Append("0");
sb.Append(M).Append("-");
if (d <= 9)
sb.Append("0");
sb.Append(d).Append("T");
if (h <= 9)
sb.Append("0");
sb.Append(h).Append(":");
if (m <= 9)
sb.Append("0");
sb.Append(m).Append(":");
if (s <= 9)
sb.Append("0");
sb.Append(s).Append("Z");
var text = sb.ToString();
return text;
}
[Benchmark]
public string CustomDev2WithMS()
{
var u = dateTime.ToUniversalTime();
var sb = new StringBuilder(23);
var y = u.Year;
var d = u.Day;
var M = u.Month;
var h = u.Hour;
var m = u.Minute;
var s = u.Second;
var ms = u.Millisecond;
sb.Append(y).Append("-");
if (M <= 9)
sb.Append("0");
sb.Append(M).Append("-");
if (d <= 9)
sb.Append("0");
sb.Append(d).Append("T");
if (h <= 9)
sb.Append("0");
sb.Append(h).Append(":");
if (m <= 9)
sb.Append("0");
sb.Append(m).Append(":");
if (s <= 9)
sb.Append("0");
sb.Append(s).Append(".");
sb.Append(ms).Append("Z");
var text = sb.ToString();
return text;
}
[Benchmark]
public string FormatO()
{
var text = dateTime.ToUniversalTime().ToString("o");
return text;
}
[Benchmark]
public string FormatS()
{
var text = string.Concat(dateTime.ToUniversalTime().ToString("s"),"Z");
return text;
}
[Benchmark]
public string FormatS_Verify()
{
var text = string.Concat(dateTime.ToUniversalTime().ToString("s"), "Z");
return text;
}
[Benchmark]
public string CustomFormatK()
{
var text = dateTime.ToUniversalTime().ToString("yyyy-MM-ddTHH:mm:ssK");
return text;
}
[Benchmark]
public string CustomFormatK_Verify()
{
var text = dateTime.ToUniversalTime().ToString("yyyy-MM-ddTHH:mm:ssK");
return text;
}
}
https://github.com/dotnet/BenchmarkDotNet đã được sử dụng
Sử dụng Newtonsoft.Json, bạn có thể làm
JsonConvert.SerializeObject(DateTime.UtcNow)
Nếu bạn đang phát triển theo SharePoint 2010 trở lên, bạn có thể sử dụng
using Microsoft.SharePoint;
using Microsoft.SharePoint.Utilities;
...
string strISODate = SPUtility.CreateISO8601DateTimeFromSystemDateTime(DateTime.Now)
.ToString("o")
hoặc, tốt hơn , $"My complicated string {dt:o}"
.
Để định dạng như 2018-06-22T13: 04: 16 có thể được thông qua trong URI của một API sử dụng:
public static string FormatDateTime(DateTime dateTime)
{
return dateTime.ToString("s", System.Globalization.CultureInfo.InvariantCulture);
}
Như đã đề cập trong câu trả lời khác, DateTime
có vấn đề theo thiết kế.
Tôi đề nghị sử dụng NodaTime để quản lý giá trị ngày / giờ:
Vì vậy, để tạo và định dạng, ZonedDateTime
bạn có thể sử dụng đoạn mã sau:
var instant1 = Instant.FromUtc(2020, 06, 29, 10, 15, 22);
var utcZonedDateTime = new ZonedDateTime(instant1, DateTimeZone.Utc);
utcZonedDateTime.ToString("yyyy-MM-ddTHH:mm:ss'Z'", CultureInfo.InvariantCulture);
// 2020-06-29T10:15:22Z
var instant2 = Instant.FromDateTimeUtc(new DateTime(2020, 06, 29, 10, 15, 22, DateTimeKind.Utc));
var amsterdamZonedDateTime = new ZonedDateTime(instant2, DateTimeZoneProviders.Tzdb["Europe/Amsterdam"]);
amsterdamZonedDateTime.ToString("yyyy-MM-ddTHH:mm:ss'Z'", CultureInfo.InvariantCulture);
// 2020-06-29T12:15:22Z
Đối với tôi NodaTime
mã trông khá dài dòng. Nhưng các loại thực sự hữu ích. Chúng giúp xử lý các giá trị ngày / thời gian chính xác.
Để sử dụng
NodaTime
vớiNewtonsoft.Json
bạn cần thêm tham chiếu đếnNodaTime.Serialization.JsonNet
gói NuGet và định cấu hình các tùy chọn JSON.
services
.AddMvc()
.AddJsonOptions(options =>
{
var settings=options.SerializerSettings;
settings.DateParseHandling = DateParseHandling.None;
settings.ConfigureForNodaTime(DateTimeZoneProviders.Tzdb);
});