317 votes

L'objet date Javascript est-il toujours décalé d'un jour ?

Dans mon application Java script, j'ai la date stockée dans un format comme celui-ci :

2011-09-24

Maintenant, lorsque j'essaie d'utiliser la valeur ci-dessus pour créer un nouvel objet Date (afin de pouvoir récupérer la date dans un format différent), la date revient toujours avec un jour d'écart. Voir ci-dessous :

var doo = new Date("2011-09-24");
console.log(doo);

journaux :

Fri Sep 23 2011 20:00:00 GMT-0400 (Eastern Daylight Time)

24 votes

La classe Date de Javascript ne représente pas une date, mais un horodatage (comme en Java). Pour en faire une date, elle utilise un fuseau horaire et c'est la cause de votre problème. Elle l'analyse avec le fuseau horaire GMT/UTC (Sep 24 2011, 00 :00 UTC) et l'édite ensuite avec un fuseau horaire différent de 4 heures (23 Sep 2011, 20 :00 GMT-0400).

3 votes

J'obtiens "date invalide". Remplacez les caractères '-' par des caractères '/' et réessayez. Ou divisez la date en plusieurs parties et définissez les composants individuellement (si vous faites cela, soustrayez 1 au numéro du mois).

0 votes

@Codo - oui, bonne réponse. L'ECMA-262 15.9.1.15 s'applique. Le PO devrait utiliser "2011-09-24T20:00:00-04:00" ou similaire.

128voto

zzzzBov Points 62084

Remarquez que l'heure d'été est -4 hours et que les heures de la date que vous récupérez sont 20 .

20h + 4h = 24h

qui est le minuit du 2011-09-24. La date était analysé en UTC (GMT) parce que vous avez fourni une chaîne de date uniquement sans indicateur de fuseau horaire. Si vous aviez fourni une chaîne date/heure sans indicateur à la place ( new Date("2011-09-24T00:00:00") ), il aurait été analysé dans votre fuseau horaire local. (Historiquement, il y a eu des incohérences à ce niveau, notamment parce que la spécification a changé plus d'une fois, mais les navigateurs modernes devraient s'en sortir ; ou vous pouvez toujours inclure un indicateur de fuseau horaire).

Vous obtenez la bonne date, vous n'avez juste pas spécifié le bon fuseau horaire.

Si vous avez besoin d'accéder aux valeurs de la date, vous pouvez utiliser getUTCDate() o l'un des autres getUTC*() fonctions :

var d,
  days;
d = new Date('2011-09-24');
days = ['Sun', 'Mon', 'Tues', 'Wed', 'Thurs', 'Fri', 'Sat'];
console.log(days[d.getUTCDay()]);

34 votes

Comment "spécifier le bon fuseau horaire" ? Le constructeur de date interprète toujours la chaîne de date comme UTC, mais s'adapte ensuite au fuseau horaire. Je peux même faire `new Date('2012-01-02 EDT') et la date est toujours reportée au jour précédent en raison de l'application du décalage pour l'heure d'été, ce qui n'a aucun sens car si je vous dis que c'est la date selon le fuseau horaire local actuel de EDT, alors n'y appliquez pas un décalage supplémentaire. Je lui ai dit que le fuseau horaire était EDT mais il applique toujours un décalage pour l'heure d'été. supplémentaire contrebalancer le retour en arrière un jour.

1 votes

@AaronLS, EDT es l'heure d'été (également appelée heure d'été) , EST est le fuseau horaire qui s'applique en janvier.

0 votes

Bien, c'est la partie amusante, écrire quelque chose de générique pour déterminer ce fuseau horaire. Parce que le but est juste de travailler avec des dates et de ne pas tenir compte de l'heure et du fuseau horaire. On peut s'amuser davantage si on a des zéros en tête avec/sans : new Date('2013-01-08') == Mon Jan 07 2013 19:00:00 GMT-0500 (Eastern Standard Time) mais new Date('2013-1-8') == Tue Jan 08 2013 00:00:00 GMT-0500 (Eastern Standard Time) . Ainsi, même si vous utilisez getTimezoneOffset pour normaliser les dates, il est préférable de s'assurer que vous avez toujours des dates/mois à deux chiffres et des 0 en tête.

79voto

AaronLS Points 12720

Pour normaliser la date et éliminer le décalage indésirable (testé ici : https://jsfiddle.net/7xp1xL5m/ ) :

var doo = new Date("2011-09-24");
console.log(  new Date( doo.getTime() + Math.abs(doo.getTimezoneOffset()*60000) )  );
// Output: Sat Sep 24 2011 00:00:00 GMT-0400 (Eastern Daylight Time)

Cette méthode permet également d'obtenir le même résultat et le mérite en revient à @tpartee (testé ici : https://jsfiddle.net/7xp1xL5m/1/ ) :

var doo = new Date("2011-09-24");
console.log( new Date( doo.getTime() - doo.getTimezoneOffset() * -60000 )  );

0 votes

J'ai dû travailler avec des dates provenant d'une API, puis les trier et les comparer. L'ajout du décalage du fuseau horaire est donc la meilleure solution.

0 votes

Cela a fonctionné pour moi, sauf que j'ai dû soustraire le timeZoneOffset, et non l'ajouter.

0 votes

@ErikAGriffin Êtes-vous dans un fuseau horaire positif, c'est-à-dire GMT+0X00 au lieu de GMT-0X00 ?

34voto

FishBasketGordo Points 14957

Je crois que cela a à voir avec le réglage du fuseau horaire. La date que vous avez créée est en GMT et l'heure par défaut est minuit, mais votre fuseau horaire est EDT, donc il soustrait 4 heures. Essayez ceci pour vérifier :

var doo = new Date("2011-09-25 EDT");

4 votes

C'est la meilleure réponse ici. +1 million de dollars pour utiliser les chaînes de localisation de fuseau horaire intégrées au lieu de convertir par programme.

2 votes

Celui-ci est utile. Cela fonctionne comme suit : $scope.dat = new Date(datestring + ' EDT'). Notez cependant la différence entre EDT et EST : lien

0 votes

Je ne sais pas ce qui se passe dans les coulisses, mais cela fonctionne parfaitement.

30voto

lincolnk Points 7124

Si vous souhaitez obtenir l'heure 0 d'une date dans le fuseau horaire local, passez les différentes parties de la date à la fonction Date constructeur.

new Date(2011,08,24); // month value is 0 based, others are 1 based.

11voto

Aleks G Points 25412

Votre problème concerne spécifiquement le fuseau horaire. Partie de la note GMT-0400 - c'est-à-dire que vous avez 4 heures de retard sur l'heure GMT. Si vous ajoutez 4 heures à la date/heure affichée, vous obtiendrez exactement minuit 2011/09/24. Utilisez toUTCString() pour obtenir la chaîne GMT :

var doo = new Date("2011-09-24");
console.log(doo.toUTCString());

Prograide.com

Prograide est une communauté de développeurs qui cherche à élargir la connaissance de la programmation au-delà de l'anglais.
Pour cela nous avons les plus grands doutes résolus en français et vous pouvez aussi poser vos propres questions ou résoudre celles des autres.

Powered by:

X