Comment créer un DateTime .NET à partir du format ISO 8601

J’ai trouvé comment transformer un DateTime en un format ISO 8601 , mais rien sur la manière de faire l’inverse en C #.

J’ai 2010-08-20T15:00:00Z , et je veux le transformer en un object DateTime .

Je pourrais séparer les parties de la chaîne moi-même, mais cela semble être beaucoup de travail pour quelque chose qui est déjà une norme internationale.

Cette solution utilise l’énumération DateTimeStyles et fonctionne également avec Z.

 DateTime d2 = DateTime.Parse("2010-08-20T15:00:00Z", null, System.Globalization.DateTimeStyles.RoundsortingpKind); 

Cela imprime la solution parfaitement.

 using System.Globalization; DateTime d; DateTime.TryParseExact( "2010-08-20T15:00:00", "s", CultureInfo.InvariantCulture, DateTimeStyles.AssumeUniversal, out d); 

Bien que MSDN indique que les formats «s» et «o» reflètent la norme, ils semblent pouvoir parsingr uniquement un sous-ensemble limité. C’est particulièrement un problème si la chaîne contient des spécifications de fuseau horaire. (Ni pour les formats de base ISO8601, ni pour les formats de précision réduits – mais ce n’est pas exactement votre cas.) C’est pourquoi je me sers de chaînes de format personnalisées pour parsingr ISO8601. Actuellement, mon extrait préféré est:

 static readonly ssortingng[] formats = { // Basic formats "yyyyMMddTHHmmsszzz", "yyyyMMddTHHmmsszz", "yyyyMMddTHHmmssZ", // Extended formats "yyyy-MM-ddTHH:mm:sszzz", "yyyy-MM-ddTHH:mm:sszz", "yyyy-MM-ddTHH:mm:ssZ", // All of the above with reduced accuracy "yyyyMMddTHHmmzzz", "yyyyMMddTHHmmzz", "yyyyMMddTHHmmZ", "yyyy-MM-ddTHH:mmzzz", "yyyy-MM-ddTHH:mmzz", "yyyy-MM-ddTHH:mmZ", // Accuracy reduced to hours "yyyyMMddTHHzzz", "yyyyMMddTHHzz", "yyyyMMddTHHZ", "yyyy-MM-ddTHHzzz", "yyyy-MM-ddTHHzz", "yyyy-MM-ddTHHZ" }; public static DateTime ParseISO8601Ssortingng ( ssortingng str ) { return DateTime.ParseExact ( str, formats, CultureInfo.InvariantCulture, DateTimeStyles.None ); } 

Si cela ne vous dérange pas d’parsingr les chaînes sans TZ (je le fais), vous pouvez append une ligne “s” pour augmenter considérablement le nombre de modifications de format couvertes.

En voici un qui fonctionne mieux pour moi (version LINQPad ):

 DateTime d; DateTime.TryParseExact( "2010-08-20T15:00:00Z", @"yyyy-MM-dd\THH:mm:ss\Z", CultureInfo.InvariantCulture, DateTimeStyles.AssumeUniversal, out d); d.ToSsortingng() 

produit

 true 8/20/2010 8:00:00 AM 

Il semble important de correspondre exactement au format de la chaîne ISO pour que TryParseExact fonctionne. Je suppose que Exact est Exact et cette réponse est évidente pour la plupart mais de toute façon …

Dans mon cas, la réponse de Reb.Cabin ne fonctionne pas car j’ai une entrée légèrement différente selon ma “valeur” ci-dessous.

Valeur: 2012-08-10T14:00:00.000Z

Il y a des milliers supplémentaires pendant des millisecondes et il peut y en avoir plus.

Cependant, si j’ajoute du .fff au format indiqué ci-dessous, tout va bien.

Chaîne de format: @"yyyy-MM-dd\THH:mm:ss.fff\Z"

Dans VS2010 Immediate Window:

 DateTime.TryParseExact(value,@"yyyy-MM-dd\THH:mm:ss.fff\Z", CultureInfo.InvariantCulture,DateTimeStyles.AssumeUniversal, out d); 

vrai

Vous devrez peut-être utiliser DateTimeStyles.AssumeLocal aussi bien en fonction de la zone où votre temps est destiné …

Cela fonctionne très bien dans LINQPad4:

 Console.WriteLine(DateTime.Parse("2010-08-20T15:00:00Z")); Console.WriteLine(DateTime.Parse("2010-08-20T15:00:00")); Console.WriteLine(DateTime.Parse("2010-08-20 15:00:00")); 

DateTime.ParseExact(...) vous permet d’indiquer à l’parsingur ce que chaque caractère représente.