web-dev-qa-db-fra.com

Obtenez l'heure GMT en Java

En Java, je veux obtenir l'heure actuelle en GMT.

J'ai essayé différentes options comme celle-ci:

Date date = new Date();
Calendar calendar = Calendar.getInstance(TimeZone.getTimeZone("GMT"));
date1 = calendar.getTime();

Mais la date est toujours interprétée dans mon fuseau horaire local.

Qu'est-ce que je fais mal et comment puis-je convertir une Java Date en GMT?

26
narayanan

Les chances sont bonnes que vous ayez fait les bonnes choses en arrière-plan pour obtenir la date, mais rien n'indique que vous n'avez pas pris cette heure GMT et que vous ne l'avez pas formatée en fonction des paramètres régionaux actuels de votre machine.

final Date currentTime = new Date();

final SimpleDateFormat sdf =
        new SimpleDateFormat("EEE, MMM d, yyyy hh:mm:ss a z");

// Give it to me in GMT time.
sdf.setTimeZone(TimeZone.getTimeZone("GMT"));
System.out.println("GMT time: " + sdf.format(currentTime));

La clé est d'utiliser votre propre DateFormat, pas le système fourni. De cette façon, vous pouvez définir le fuseau horaire du DateFormat sur ce que vous souhaitez, au lieu d'être défini sur le fuseau horaire du Locale.

34
Edwin Buck

Je me demande pourquoi personne ne fait ça:

Calendar time = Calendar.getInstance();
time.add(Calendar.MILLISECOND, -time.getTimeZone().getOffset(time.getTimeInMillis()));
Date date = time.getTime();

Mise à jour: depuis Java 8,9,10 et plus, il devrait y avoir de meilleures alternatives prises en charge par Java. Merci pour votre commentaire @humanity

19
Harun

D'après mon expérience, les classes d'agenda et de date regroupées dans Java peuvent produire un effet sous-désiré. Si cela ne vous dérange pas de passer à Java 8, envisagez d'utiliser ZonedDateTime

ainsi:

ZonedDateTime currentDate = ZonedDateTime.now( ZoneOffset.UTC );
7
Damilola

tl; dr

Instant.now()

Java.time

La réponse de Damilola est correcte en vous suggérant d'utiliser le framework Java.time intégré à Java 8 et versions ultérieures. Mais cette réponse utilise le ZonedDateTime classe qui est exagérée si vous voulez juste UTC plutôt qu'un fuseau horaire particulier.

Les anciennes classes de date-heure gênantes sont désormais héritées, supplantées par les classes Java.time.

Instant

La classe Instant représente un moment de la chronologie dans [~ # ~] utc [~ # ~] avec une résolution de nanosecondes (jusqu'à neuf (9) chiffres d'une fraction décimale).

Code simple:

Instant instant = Instant.now() ;

instant.toString (): 2016-11-29T23: 18: 14.604Z

Vous pouvez considérer Instant comme le bloc de construction auquel vous pouvez ajouter un fuseau horaire (ZoneID) pour obtenir un ZonedDateTime.

ZoneId z = ZoneId.of( "America/Montreal" );
ZonedDateTime zdt = instant.atZone( z );

À propos de Java.time

Le cadre Java.time est intégré à Java 8 et versions ultérieures. Ces classes supplantent l'ancien héritage gênant classes date-heure telles que Java.util.Date , Calendar , & SimpleDateFormat .

Le projet Joda-Time , désormais en mode de maintenance , conseille la migration vers Java.time.

Pour en savoir plus, consultez le Oracle Tutorial . Et recherchez Stack Overflow pour de nombreux exemples et explications. La spécification est JSR 310 .

Où obtenir les classes Java.time?

Le projet ThreeTen-Extra étend Java.time avec des classes supplémentaires. Ce projet est un terrain d'essai pour de futurs ajouts possibles à Java.time. Vous pouvez trouver ici des classes utiles telles que Interval , YearWeek , YearQuarter et plus .

5
Basil Bourque

Pour obtenir l'heure en millisecondes au GMT, tout ce dont vous avez besoin est

long millis = System.currentTimeMillis();

Vous pouvez aussi faire

long millis = new Date().getTime();

et

long millis = 
    Calendar.getInstance(TimeZone.getTimeZone("GMT")).getTimeInMillis();

mais ce sont des moyens inefficaces de faire le même appel.

2
Peter Lawrey

Après avoir essayé beaucoup de méthodes, j'ai découvert que pour obtenir le temps en millis à GMT, vous devez créer deux objets SimpleDateFormat distincts, un pour le formatage en GMT et un autre pour l'analyse.

Voici le code:

 SimpleDateFormat format = new SimpleDateFormat("yyyy-MM-dd HH:mm:ss");
 format.setTimeZone(TimeZone.getTimeZone("UTC"));
 Date date = new Date();
 SimpleDateFormat dateParser = new SimpleDateFormat("yyyy-MM-dd HH:mm:ss");
 Date dateTime= dateParser.parse(format.format(date));
 long gmtMilliSeconds = dateTime.getTime();

Cela fonctionne bien. :)

2
Firdous Ahmad

Tu ne peux pas

Tout d'abord, vous demandez l'impossible. Un objet Date à l'ancienne n'a pas été obtenu, car il ne peut pas avoir de fuseau horaire ni de décalage GMT.

Mais la date est toujours interprétée dans mon fuseau horaire local.

Je suppose que vous avez imprimé la Date ou fait quelque chose d'autre qui l'appelle implicitement la méthode toString. Je crois que c'est la seule fois que le Date est interprété dans votre fuseau horaire. Plus précisément dans le fuseau horaire par défaut actuel de votre JVM. En revanche, cela est inévitable. Date.toString() se comporte de cette manière, il récupère le paramètre de fuseau horaire de la JVM et l'utilise pour rendre la chaîne à renvoyer.

Vous pouvez avec Java.time

Cependant, vous ne devez pas utiliser un Date. Cette classe est mal conçue et heureusement dépassée depuis longtemps. Aussi Java.time, la moderne Java API de date et d'heure qui la remplace, a une classe ou deux pour les dates et heures avec décalage par rapport à GMT ou UTC. Je considère également GMT et UTC pour l'instant, à proprement parler ils ne le sont pas.

    OffsetDateTime now = OffsetDateTime.now(ZoneOffset.UTC);
    System.out.println("Time now in UTC (GMT) is " + now);

Lorsque j'ai exécuté cet extrait de code tout à l'heure, la sortie était:

L'heure en UTC (GMT) est le 2019-06-17T11: 51: 38.246188Z

Le Z de fin de la sortie signifie UTC.

Liens

1
Ole V.V.

Après Java 8, vous voudrez peut-être obtenir l'heure formatée comme ci-dessous:

DateTimeFormatter.ofPattern("HH:mm:ss.SSS").format(LocalTime.now(ZoneId.of("GMT")));
0
Denis Wang

C'est assez simple et direct.

Date date = new Date();
TimeZone.setDefault(TimeZone.getTimeZone("GMT"));
Calendar cal = Calendar.getInstance(TimeZone.getDefault());
date = cal.getTime();

Maintenant, la date contiendra l'heure GMT actuelle.

0
HeisenBerg

Méthodes Utils utiles comme ci-dessous pour gérer le temps en GMT avec des économies DST:

public static Date convertToGmt(Date date) {
    TimeZone tz = TimeZone.getDefault();
    Date ret = new Date(date.getTime() - tz.getRawOffset());

    // if we are now in DST, back off by the delta.  Note that we are checking the GMT date, this is the KEY.
    if (tz.inDaylightTime(ret)) {
        Date dstDate = new Date(ret.getTime() - tz.getDSTSavings());

        // check to make sure we have not crossed back into standard time
        // this happens when we are on the cusp of DST (7pm the day before the change for PDT)
        if (tz.inDaylightTime(dstDate)) {
            ret = dstDate;
        }
    }
    return ret;
}

public static Date convertFromGmt(Date date) {
    TimeZone tz = TimeZone.getDefault();
    Date ret = new Date(date.getTime() + tz.getRawOffset());

    // if we are now in DST, back off by the delta.  Note that we are checking the GMT date, this is the KEY.
    if (tz.inDaylightTime(ret)) {
        Date dstDate = new Date(ret.getTime() + tz.getDSTSavings());

        // check to make sure we have not crossed back into standard time
        // this happens when we are on the cusp of DST (7pm the day before the change for PDT)
        if (tz.inDaylightTime(dstDate)) {
            ret = dstDate;
        }
    }
    return ret;
}
0
Kalpesh