web-dev-qa-db-fra.com

DateTime.ToString ("MM / jj / aaaa HH: mm: ss.fff") a généré quelque chose comme "09/14/2013 07.20.31.371"

J'ai une application WP8 qui envoie l'heure actuelle à un service Web.

Je reçois la chaîne datetime en appelant

DateTime.ToString("MM/dd/yyyy HH:mm:ss.fff")

Pour la plupart des utilisateurs, cela fonctionne très bien et me donne la chaîne correcte comme "09/10/2013 04:04:31.415". Mais pour certains utilisateurs, la chaîne résultante est quelque chose comme "09/14/2013 07.20.31.371", ce qui pose problème dans mon service Web.

Est-ce à cause d'un problème de format de culture? Comment puis-je m'assurer que la chaîne de résultat est délimitée par deux points au lieu de point?

123
Eldorado

Est-ce à cause d'un problème de format de culture?

Oui. Votre utilisateur doit être dans une culture où le séparateur d'heure est un point. ":" Et "/" sont tous deux interprétés en fonction de la culture dans formats de date et d'heure personnalisés .

Comment puis-je m'assurer que la chaîne de résultat est délimitée par deux points au lieu de point?

Je suggèrerais de spécifier CultureInfo.InvariantCulture:

string text = dateTime.ToString("MM/dd/yyyy HH:mm:ss.fff",
                                CultureInfo.InvariantCulture);

Alternativement, vous pourriez simplement citer les séparateurs d'heure et de date:

string text = dateTime.ToString("MM'/'dd'/'yyyy HH':'mm':'ss.fff");

... mais cela vous donnera des résultats "intéressants" auxquels vous ne vous attendez probablement pas si vous faites fonctionner des utilisateurs dans une culture où le système de calendrier par défaut n'est pas le calendrier grégorien. Par exemple, prenons le code suivant:

using System;
using System.Globalization;
using System.Threading;

class Test
{
    static void Main()        
    {
        DateTime now = DateTime.Now;
        CultureInfo culture = new CultureInfo("ar-SA"); // Saudi Arabia
        Thread.CurrentThread.CurrentCulture = culture;
        Console.WriteLine(now.ToString("yyyy-MM-ddTHH:mm:ss.fff"));
    }
} 

Cela produit une sortie (le 18 septembre 2013) de:

11/12/1434 15:04:31.750

J'imagine que votre service Web serait surpris par cela!

En fait, je suggérerais non seulement d'utiliser la culture invariante, mais également de changer en un format de date ISO-8601:

string text = dateTime.ToString("yyyy-MM-ddTHH:mm:ss.fff");

C'est un format plus largement accepté - il est également triable et rend évident l'ordre du mois et du jour. (Alors que 06/07/2013 peut être interprété comme le 7 juin ou le 6 juillet selon la culture du lecteur.)

229
Jon Skeet

: a une signification particulière: il est le séparateur d'heure. ( chaînes de format de date et d'heure personnalisées ).

Utilisez \ pour l’échapper:

DateTime.ToString(@"MM/dd/yyyy HH\:mm\:ss.fff")

Ou utilisez CultureInfo.InvariantCulture:

DateTime.ToString("MM/dd/yyyy HH:mm:ss.fff", CultureInfo.InvariantCulture)

Je suggérerais d’aller avec le second, parce que / a également une signification spéciale (c’est le séparateur de date. ), vous pouvez donc avoir des problèmes avec ça aussi.

9
MarcinJuraszek

Vous pouvez utiliser InvariantCulture car votre utilisateur doit appartenir à une culture utilisant un point au lieu de deux points:

DateTime.ToString("MM/dd/yyyy HH:mm:ss.fff", CultureInfo.InvariantCulture);
7
Jon La Marr

Récemment, je suis tombé sur ce problème avec Windows 10 depuis dans une autre direction et j'ai trouvé la réponse de @JonSkeet très utile pour résoudre mon problème.

J'ai également fait quelques recherches supplémentaires avec un formulaire de test et constaté que lorsque la culture actuelle était définie sur "no" ou "nb-NO" à l'exécution (Thread.CurrentThread.CurrentCulture = new CultureInfo("no");), le paramètre ToString ("yyyy-MM- dd HH: mm: ss ") l’appel a répondu différemment sous Windows 7 et Windows 10. Il a donné ce que j’attendais sous Windows 7 et HH.mm.ss sous Windows 10!

Je pense que c'est un peu effrayant! Depuis que je croyais qu'une culture était une culture dans n'importe quelle version de Windows au moins.

6
Håkon Seljåsen

Vous pouvez utiliser String.Format:

DateTime d = DateTime.Now;
string str = String.Format("{0:00}/{1:00}/{2:0000} {3:00}:{4:00}:{5:00}.{6:000}", d.Month, d.Day, d.Year, d.Hour, d.Minute, d.Second, d.Millisecond);
// I got this result: "02/23/2015 16:42:38.234"
4
Cosmin

Convertir la date en chaîne

Utiliser le nom Space

using System.Globalization;

Code

string date = DateTime.ParseExact(datetext.Text, "dd-MM-yyyy", CultureInfo.InstalledUICulture).ToString("yyyy-MM-dd");
0
Hafsal