ให้วัตถุ DateTime ฉันจะได้รับวันที่ ISO 8601 ในรูปแบบสตริงได้อย่างไร


790

ได้รับ:

DateTime.UtcNow

ฉันจะรับสตริงที่แสดงค่าเดียวกันในรูปแบบISO 8601 ได้อย่างไร

โปรดทราบว่า ISO 8601 กำหนดรูปแบบที่คล้ายคลึงกันจำนวนหนึ่ง รูปแบบเฉพาะที่ฉันกำลังมองหาคือ:

yyyy-MM-ddTHH:mm:ssZ

คำตอบ:


780

หมายเหตุถึงผู้อ่าน: ผู้แสดงความคิดเห็นหลายคนชี้ให้เห็นปัญหาบางอย่างในคำตอบนี้ (เกี่ยวข้องโดยเฉพาะกับข้อเสนอแนะแรก) อ้างถึงส่วนความคิดเห็นสำหรับข้อมูลเพิ่มเติม

DateTime.UtcNow.ToString("yyyy-MM-ddTHH\\:mm\\:ss.fffffffzzz");

นี้จะช่วยให้คุณวันที่คล้ายกับ2008-09-22T13: 57: 31.2311892-04: 00

อีกวิธีคือ:

DateTime.UtcNow.ToString("o");

ซึ่งให้คุณ2008-09-22T14: 01: 54.9571247Z

เพื่อให้ได้รูปแบบที่ระบุคุณสามารถใช้:

DateTime.UtcNow.ToString("yyyy-MM-ddTHH:mm:ssZ")

ตัวเลือกการจัดรูปแบบ DateTime


20
ทุกวันนี้การทำเช่นนั้น (พยายามแสดงเวลา UTC ด้วยออฟเซ็ตซึ่งไม่สมเหตุสมผล) ทำให้เกิดข้อยกเว้น ดังนั้นฉันเห็นด้วยกับคนอื่น ๆ ว่ารูปแบบ "s" กับวัฒนธรรมที่ไม่เปลี่ยนแปลงนั้นน่าจะถูกต้องมากขึ้น FYI ข้อความของ formatexception คือ: "UTC DateTime กำลังถูกแปลงเป็นข้อความในรูปแบบที่ถูกต้องสำหรับเวลาท้องถิ่นเท่านั้นซึ่งสามารถเกิดขึ้นได้เมื่อเรียก DateTime เพื่อ ToString โดยใช้ตัวระบุรูปแบบ 'z' ซึ่งจะรวมการชดเชยโซนเวลาท้องถิ่น ในผลลัพธ์ "
Tom Lianza

9
ฉันอาศัยอยู่ในออสเตรเลียและสำหรับฉันฉันต้องใช้ToString("yyyy-MM-ddTHH:mm:ssK")เพื่อการทำงาน (กับปลั๊กอินเวลา jquery timeago ที่ฉันใช้)
GONeale

6
หากคุณต้องการรวมเขตเวลาชดเชยให้ทำสิ่งนี้: dt.ToString("s") + dt.ToString("zzz")// 2013-12-05T07: 19: 04-08: 00
alekop

4
เครื่องหมายทับ (\ :) ทำให้เกิดปัญหากับสตริง ... ใส่อักขระ @ เพื่อใช้ตัวอักษรสตริงแทน
Gigi

6
@core: นั่นเป็นหนึ่งในรูปแบบมาตรฐานซึ่งแตกต่างจากรูปแบบที่กำหนดเองที่เชื่อมโยง: msdn.microsoft.com/en-us/library/az4se3k1(v=vs.110).aspx
Wayne

361

DateTime.UtcNow.ToString("s", System.Globalization.CultureInfo.InvariantCulture)ควรให้สิ่งที่คุณต้องการด้วยตัวระบุรูปแบบ "s" อธิบายว่าเป็นรูปแบบวันที่ / เวลาที่เรียงลำดับได้ เป็นไปตามมาตรฐาน ISO 8601


34
ฉันเชื่อว่านี่เป็นคำตอบที่ถูกต้อง ไม่มีจุดใดในการกำหนด yyyy-MM-etc อย่างชัดเจนหาก Microsoft ได้นำ ISO 8601 ไปใช้แล้วการตอบสนองของ Iain นั้นถูกต้องเช่นกัน แต่คุณควรระบุ InvariantCulture (หรือ CultureInfo อื่น ๆ ) ด้วยเหตุผลหลายประการ (เช่นไม่เคยสมมติว่า. NET แค่สมมติ) คุณสามารถใช้: DateTime.UtcNow.ToString(CultureInfo.InvariantCulture.DateTimeFormat.SortableDateTimePattern); อย่างไรก็ตามเนื่องจากสิ่งเหล่านี้ไม่รวมเขตเวลา ฯลฯ คุณอาจไม่มีทางเลือกนอกจากใช้ตัวจัดรูปแบบที่ชัดเจนเช่น"yyyy-MM-ddTHH:mm:ss.fffZ"
Jon Davis

20
แม้ว่าจะเป็นไปตามเงื่อนไข แต่จะทำให้เขตเวลาหมดไปและมีZลักษณะเช่นนี้: DateTime.UtcNow.ToString(c, CultureInfo.InvariantCulture)) => 2012-06-26T11:55:36และไม่มีความละเอียดเป็นมิลลิวินาทีที่ดีมากเนื่องจากคอมพิวเตอร์ทำจำนวนเห็บต่อวินาทีอย่างยุติธรรม
Henrik

9
เมื่อoคุณได้รับ2012-06-26T11:55:36.1007668Zความหมายใน36.1007668วินาทีคุณจึงได้ความละเอียดลดลงเหลือ1/10^7หนึ่งวินาที จาก 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 (.)
Henrik


2
@binki - ตอนนี้ฉันสับสนมาก ตามเอกสารที่ฉันเชื่อมโยงก่อนหน้านี้สำหรับ SortableDateTimePatternมันบอกว่ามันควรจะเป็นวัฒนธรรมที่เฉพาะเจาะจง อย่างไรก็ตามดูเหมือนว่าจะขัดแย้งกับตัวอย่างของตัวเอง (เนื่องจากพวกเขาทั้งหมดมีลักษณะเหมือนกัน); DateTime.Now.ToString("s", new CultureInfo(myCulture))ความพยายาม
drzaus

87
DateTime.UtcNow.ToString("s")

ส่งคืนบางสิ่งเช่น 2008-04-10T06: 30: 00

UtcNowเห็นได้ชัดว่าส่งคืนเวลา UTCดังนั้นจึงไม่มีอันตรายใด ๆ ใน:

string.Concat(DateTime.UtcNow.ToString("s"), "Z")

11
เพิ่งหมดดอกเบี้ย: ทำไมต้อง string.Concat () มากกว่า '+'
Daniel Fortunov

2
Habbit มีความแตกต่างไหม?
Iain

84
@ KonZomers: ฉันไม่คิดว่าถูกต้อง ฉันคิดว่าa + bคอมไพล์รหัสกลางเหมือนกันstring.Concat(a, b)(สมมติว่า a และ b เป็นสตริงแน่นอน) ดังนั้นจึงไม่มีความแตกต่างด้านประสิทธิภาพหรือการใช้หน่วยความจำ
Mark Byers

78
ใช่มาร์คถูกต้อง Koen คุณเพิ่งตกหลุมพรางของการเพิ่มประสิทธิภาพขนาดเล็กที่ไร้เหตุผลแม้ว่าคุณจะถูกต้องก็ตาม
Noldorin

7
@ greg84: ใช่คุณไม่ถูกต้องทั้งหมด ดูโพสต์นี้โดยสถาปนิกของ Microsoft Rico Mariani: blogs.msdn.com/b/ricom/archive/2003/12/15/43628.aspx - เขาบอกว่า a + b รวบรวมเพื่อ concat + มีข้อมูลเพิ่มเติมเกี่ยวกับการใช้งานที่เหมาะสมของ StringBuilder
mrówa

37

ใช้:

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

แหล่งที่มา:


2
ดูเหมือนว่าคุณจะตกเป็นเหยื่อของการทำสำเนาที่ประเพณีท้องถิ่น ;-) string strLocalTimeAndOffset_custom = localTimeAndOffset.ToString("yyyy-MM-ddTHH:mm:ssK");จะส่งผลให้:strLocalTimeAndOffset_custom: 2012-09-17T22:02:51-07:00
ฮอลลี่

oเป็นรูปแบบ ISO-8601
Yousha Aleayoub

33
System.DateTime.UtcNow.ToString("o")

=>

val it : string = "2013-10-13T13:03:50.2950037Z"

เห็นด้วยนี่เป็นวิธีเดียวที่จะมั่นใจได้ว่าคุณมีวันที่ / เวลาที่ชัดเจนในทุกเขตเวลา
Matt Wilko

23

คุณสามารถรับ "Z" ( ISO 8601 UTC ) ด้วยรหัสถัดไป:

Dim tmpDate As DateTime = New DateTime(Now.Ticks, DateTimeKind.Utc)
Dim res as String = tmpDate.toString("o") '2009-06-15T13:45:30.0000000Z


นี่คือเหตุผล:

ISO 8601 มีรูปแบบที่ต่างกัน:

DateTimeKind.Local

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 ให้เรา enum ด้วยตัวเลือกเหล่านั้น:

'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")

หมายเหตุ : ถ้าคุณใช้ Visual Studio 2008 "watch utility" กับtoString ("o")คุณอาจได้รับผลลัพธ์ที่แตกต่างฉันไม่รู้ว่ามันเป็นข้อบกพร่องหรือไม่ แต่ในกรณีนี้คุณจะได้ผลลัพธ์ที่ดีขึ้นโดยใช้ตัวแปร String หากคุณกำลังดีบัก

แหล่งที่มา: สตริงรูปแบบวันที่และเวลามาตรฐาน (MSDN)


20

หากคุณต้องใช้ DateTime กับ ISO 8601 ดังนั้น ToString ("o") ควรให้ผลลัพธ์ที่คุณต้องการ ตัวอย่างเช่น,

2015-07-06T12:08:27

อย่างไรก็ตาม DateTime + TimeZone อาจมีปัญหาอื่น ๆ ตามที่อธิบายไว้ในบล็อกโพสต์DateTime และ DateTimeOffset ใน. NET: แนวทางปฏิบัติที่ดีและข้อผิดพลาดทั่วไป :

DateTime มีกับดักนับไม่ถ้วนที่ออกแบบมาเพื่อให้โค้ดของคุณบกพร่อง:

1.- ค่า DateTime กับ DateTimeKind ไม่ระบุเป็นข่าวร้าย

2.- DateTime ไม่สนใจ UTC / Local เมื่อทำการเปรียบเทียบ

3.- ค่า DateTime ไม่ทราบถึงสตริงรูปแบบมาตรฐาน

4.- การแยกสตริงที่มีเครื่องหมาย UTC ด้วย DateTime ไม่รับประกันเวลา UTC


2
ISO8601 ถูกใช้ใน strava สำหรับหนึ่ง อย่างไรก็ตามโปรดใช้: StartTime.ToString ("yyyy-MM-ddTHH: mm: ssZ") มากกว่า ToString ("o") ซึ่งเพิ่มมิลลิวินาที ฯลฯ
peterincumbria

2
สำหรับฉัน "yyyy-MM-dd-THH: mm: ssZ" เอาท์พุทอักษร "Z" ที่ท้ายสตริงของฉันแทนที่จะเป็นตัวระบุเขตเวลาซึ่งไม่ได้ทำสิ่งที่ฉันต้องการ ToString ("o") ทำสิ่งที่ฉันต้องการได้ง่ายขึ้นและสั้นลง
แบลร์คอน

18

ประหลาดใจที่ไม่มีใครแนะนำ:

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

UniversalSortableDateTimePatternทำให้คุณได้รับเกือบทุกวิธีที่จะสิ่งที่คุณต้องการ (ซึ่งเป็นมากขึ้นRFC 3339เป็นตัวแทน)


เพิ่ม: ฉันตัดสินใจที่จะใช้การวัดประสิทธิภาพที่อยู่ในคำตอบhttps://stackoverflow.com/a/43793679/653058เพื่อเปรียบเทียบประสิทธิภาพการทำงานของ

TL: ดร; มันอยู่ที่ปลายแพง แต่ก็ยังคงเพียงเล็กน้อยกว่าครึ่งมิลลิวินาทีในแล็ปท็อปเก่าของฉันเร็ว :-)

การดำเนินงาน:

[Benchmark]
public string ReplaceU()
{
   var text = dateTime.ToUniversalTime().ToString("u").Replace(' ', 'T');
   return text;
}

ผล:

// * 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 *****

1
คำตอบที่ยอมรับของ "o" ทำงานได้ แต่ให้ความแม่นยำในระดับที่น่ารำคาญ (geez .XXXXXXX วินาที) ในขณะที่ฉันชอบสิ่งนี้เพราะมันหยุดในไม่กี่วินาที
jhocking

นอกจากนี้เอกสารที่อ้างว่า "u" คือ ISO 8601 แต่มีพื้นที่แทน T หรือไม่ รวมเข้าด้วยกัน microsoft
jhocking

@jhocking en.wikipedia.org/wiki/ISO_8601#cite_note-30 ISO 8601 นั้นค่อนข้างอนุญาตหากคุณอ่านมัน ...
rburte

16

ฉันแค่จะใช้XmlConvert:

XmlConvert.ToString(DateTime.UtcNow, XmlDateTimeSerializationMode.RoundtripKind);

มันจะรักษาเขตเวลาโดยอัตโนมัติ


ฉันไปข้างหน้าและเพิ่มวิธีการขยาย คลาสคงที่สาธารณะ DateTimeExtensions {สตริงคงที่สาธารณะ ToIsoFormat (DateTime dateTime นี้) {ส่งคืน XmlConvert.ToString (dateTime, XmlDateTimeSerializationMode.RoundtripKind); }}
muruge

14

คำตอบส่วนใหญ่เหล่านี้มีมิลลิวินาที / microsecond ซึ่งไม่สนับสนุน ISO 8601 อย่างชัดเจนคำตอบที่ถูกต้องคือ:

System.DateTime.Now.ToString("yyyy-MM-ddTHH:mm:ssK");
// or
System.DateTime.Now.ToUniversalTime().ToString("yyyy-MM-ddTHH:mm:ssK");

อ้างอิง:


15
อ่านลิงค์ Wikipedia ของคุณเองภายใต้ "Times" มันพูดถึง "เศษส่วนทศนิยม" หมายถึง ISO 8601 รองรับทั้งมิลลิวินาทีและไมโครวินาที (แต่ฝ่ายสื่อสารอาจ จำกัด จำนวนตำแหน่งทศนิยมที่ยอมรับ)
Søren Boisen

11
DateTime.Now.ToString("yyyy-MM-dd'T'HH:mm:ss zzz");

DateTime.Now.ToString("O");

หมายเหตุ: ขึ้นอยู่กับการแปลงที่คุณทำในตอนท้ายคุณจะใช้บรรทัดแรก (ส่วนใหญ่ชอบ) หรือบรรทัดที่สอง

ตรวจสอบให้แน่ใจว่าใช้รูปแบบเฉพาะเวลาท้องถิ่นเนื่องจาก "zzz" เป็นข้อมูลเขตเวลาสำหรับการแปลง UTC

ภาพ


ผมไม่แน่ใจว่า #ChrisHynes ตั้งแต่เขาถูกถามเกี่ยวกับข้อเสนอแนะที่ผมทำเกี่ยวกับบรรทัดแรกของรหัส แต่ถ้าคุณมีความถูกต้องและเป็นกรณีที่คำตอบคือ "ReSharper"
PSM

9

ตัว"s"ระบุรูปแบบมาตรฐานแสดงถึงสตริงรูปแบบวันที่และเวลาที่กำหนดเองที่กำหนดโดยคุณสมบัติDateTimeFormatInfo.SortableDateTimePattern รูปแบบสะท้อนถึงมาตรฐานที่กำหนด ( ISO 8601 ) และคุณสมบัติเป็นแบบอ่านอย่างเดียว ดังนั้นจึงเป็นแบบเดียวกันเสมอโดยไม่คำนึงถึงวัฒนธรรมที่ใช้หรือผู้ให้บริการรูปแบบที่ให้มา "yyyy'-'MM'-'dd'T'HH':'mm':'ss"สตริงรูปแบบที่กำหนดเอง

เมื่อใช้ตัวระบุรูปแบบมาตรฐานนี้การดำเนินการจัดรูปแบบหรือการแยกวิเคราะห์จะใช้วัฒนธรรมที่ไม่เปลี่ยนแปลงเสมอ

- จากMSDN


1
ดังนั้นมันก็โอเคที่จะใช้.ToString("s")?
AhmetB - Google

ฉันเชื่ออย่างนั้น - ตราบใดที่ความต้องการของคุณตรงกับคำถามเดิมนั่นคือ .. แต่ให้ดูคำเตือนโดยไซมอนวิลสันด้านล่าง
Amal

9

ในการแปลง DateTime.UtcNow เป็นสตริงแสดงyyyy-MM-ddTHH: mm: ssZคุณสามารถใช้วิธี ToString () ของโครงสร้าง DateTime ด้วยสตริงการจัดรูปแบบที่กำหนดเอง เมื่อใช้สตริงรูปแบบที่กำหนดเองกับ DateTime เป็นสิ่งสำคัญที่ต้องจำไว้ว่าคุณต้องหลบเลี่ยง seperators โดยใช้เครื่องหมายคำพูดเดี่ยว

ต่อไปนี้จะคืนค่าการแทนค่าสตริงที่คุณต้องการ:

DateTime.UtcNow.ToString("yyyy'-'MM'-'dd'T'HH':'mm':'ss'Z'", DateTimeFormatInfo.InvariantInfo)

9

เป็นที่น่าสนใจว่ารูปแบบที่กำหนดเอง "yyyy-MM-ddTHH: mm: ssK" (ไม่มี ms) เป็นวิธีการจัดรูปแบบที่รวดเร็วที่สุด

นอกจากนี้ยังเป็นที่น่าสนใจว่ารูปแบบ "S" นั้นช้าในแบบคลาสสิกและเร็วบน Core ...

แน่นอนว่าตัวเลขนั้นใกล้เคียงกันมากความแตกต่างระหว่างแถวบางแถวนั้นไม่มีนัยสำคัญ (การทดสอบที่มีคำต่อท้าย_Verifyเหมือนกับที่ไม่มีคำต่อท้ายนั้นแสดงให้เห็นถึงผลลัพธ์การทำซ้ำ)

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 |

รหัส:

    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ถูกนำมาใช้



2

หากคุณกำลังพัฒนาภายใต้SharePoint 2010หรือสูงกว่าคุณสามารถใช้

using Microsoft.SharePoint;
using Microsoft.SharePoint.Utilities;
...
string strISODate = SPUtility.CreateISO8601DateTimeFromSystemDateTime(DateTime.Now)

20
SharePoint เมื่อ. Net ของคุณยังไม่เพียงพอ
Henrik

18
การใช้ SharePoint สำหรับสิ่งนี้เป็นเหมือนการนำอ่างวุ้นกล่องไม้เปียกน้ำและลิงชิมแปนซีที่เดินเร็ว 2 หลังเพื่อต่อสู้กับปืน
nathanchere

แม้ใน SharePoint หวังว่าคุณสามารถใช้ BCL ของหรือดีกว่า.ToString("o") $"My complicated string {dt:o}"
binki

2

ในการจัดรูปแบบเช่น2018-06-22T13: 04: 16ซึ่งสามารถส่งผ่านใน URI ของ API ใช้:

public static string FormatDateTime(DateTime dateTime)
{
    return dateTime.ToString("s", System.Globalization.CultureInfo.InvariantCulture);
}

1
ฉันคิดว่าสตริงวันที่ ISO นี้เป็นค่าคงที่ของวัฒนธรรมต่อคำจำกัดความ
Jonas

1

ดังที่กล่าวไว้ในคำตอบอื่น ๆDateTimeมีปัญหาจากการออกแบบ

NodaTime

ฉันแนะนำให้ใช้NodaTimeเพื่อจัดการค่าวันที่ / เวลา:

  • เวลาท้องถิ่นวันที่และเวลา
  • เวลาทั่วโลก
  • เวลากับเขตเวลา
  • ระยะเวลา
  • ระยะเวลา

การจัดรูปแบบ

ดังนั้นในการสร้างและจัดรูปแบบZonedDateTimeคุณสามารถใช้ข้อมูลโค้ดต่อไปนี้:

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

สำหรับฉันNodaTimeรหัสดูเหมือน verbose ค่อนข้าง แต่ประเภทนั้นมีประโยชน์จริงๆ ช่วยจัดการค่าวันที่ / เวลาได้อย่างถูกต้อง

Newtonsoft.Json

หากต้องการใช้NodaTimeกับNewtonsoft.Jsonคุณต้องเพิ่มการอ้างอิงถึงNodaTime.Serialization.JsonNetแพ็คเกจ NuGet และกำหนดค่าตัวเลือก JSON

services
    .AddMvc()
    .AddJsonOptions(options =>
    {
        var settings=options.SerializerSettings;
        settings.DateParseHandling = DateParseHandling.None;
        settings.ConfigureForNodaTime(DateTimeZoneProviders.Tzdb);
    });
โดยการใช้ไซต์ของเรา หมายความว่าคุณได้อ่านและทำความเข้าใจนโยบายคุกกี้และนโยบายความเป็นส่วนตัวของเราแล้ว
Licensed under cc by-sa 3.0 with attribution required.