Ajouter n heures à une date en Java?


136

Comment ajouter n heures à un objet Date? J'ai trouvé un autre exemple utilisant des jours sur StackOverflow, mais je ne comprends toujours pas comment le faire avec des heures.


3
Utilisez joda-time.sourceforge.net , si possible.
Babar

3
Utilisez la date et l'heure Java 8 si possible.
peceps

@Babar FYI, le projet Joda-Time est désormais en mode maintenance , l'équipe conseillant la migration vers les classes java.time . Voir le didacticiel d'Oracle .
Basil Bourque

Réponses:


210

Vérifiez la classe de calendrier. Il a une addméthode (et quelques autres) pour permettre la manipulation du temps. Quelque chose comme ça devrait fonctionner.

    Calendar cal = Calendar.getInstance(); // creates calendar
    cal.setTime(new Date()); // sets calendar time/date
    cal.add(Calendar.HOUR_OF_DAY, 1); // adds one hour
    cal.getTime(); // returns new date object, one hour in the future

Consultez l' API pour en savoir plus.


4
Faites juste attention si vous avez affaire à l'heure d'été ou à l'heure d'été.
CurtainDog

5
Inutile de mentionner que vous pouvez ajouter des "heures négatives"
pramodc84

6
@CurtainDog Using Calendar.add()s'en charge automatiquement.
Jesper

6
cal.setTime (new Date ()) n'est pas nécessaire - le javadoc de Calendar.getInstance () dit: "Le calendrier renvoyé est basé sur l'heure actuelle dans le fuseau horaire par défaut avec les paramètres régionaux par défaut."
mithrandir

Pour info, les anciennes classes de date-heure gênantes telles que java.util.Date, java.util.Calendaret java.text.SimpleDateFormatsont maintenant héritées , supplantées par les classes java.time intégrées à Java 8 et Java 9. Voir le didacticiel d'Oracle .
Basil Bourque

82

Si vous utilisez Apache Commons / Lang , vous pouvez le faire en une seule étape en utilisant DateUtils.addHours():

Date newDate = DateUtils.addHours(oldDate, 3);

(L'objet d'origine est inchangé)


3
Vous pouvez également utiliser les heures négatives:DateUtils.addHours(oldDate, -1);
Kaptain

Dans les coulisses, cela fait exactement ce que fait la réponse de Nikita, mais c'est très simple et facile à lire. De plus, si vous utilisez déjà Apache Commons / Lang ... pourquoi pas?
Matt

28

Pour simplifier l'exemple de @ Christopher.

Dis que tu as une constante

public static final long HOUR = 3600*1000; // in milli-seconds.

Tu peux écrire.

Date newDate = new Date(oldDate.getTime() + 2 * HOUR);

Si vous utilisez long pour stocker la date / l'heure au lieu de l'objet Date, vous pouvez le faire

long newDate = oldDate + 2 * HOUR;

27

tl; dr

myJavaUtilDate.toInstant()
              .plusHours( 8 )

Ou…

myJavaUtilDate.toInstant()                // Convert from legacy class to modern class, an `Instant`, a point on the timeline in UTC with resolution of nanoseconds.
              .plus(                      // Do the math, adding a span of time to our moment, our `Instant`. 
                  Duration.ofHours( 8 )   // Specify a span of time unattached to the timeline.
               )                          // Returns another `Instant`. Using immutable objects creates a new instance while leaving the original intact.

Utilisation de java.time

Le framework java.time intégré à Java 8 et versions ultérieures remplace les anciennes classes Java.util.Date/.Calendar. Ces anciennes classes sont notoirement gênantes. Évite-les.

Utilisez la toInstantméthode récemment ajoutée à java.util.Date pour convertir de l'ancien type au nouveau type java.time. An Instantest un moment sur la ligne du temps en UTC avec une résolution de nanosecondes .

Instant instant = myUtilDate.toInstant();

Vous pouvez ajouter des heures à cela Instanten passant un TemporalAmounttel que Duration.

Duration duration = Duration.ofHours( 8 );
Instant instantHourLater = instant.plus( duration );

Pour lire cette date-heure, générez une chaîne au format standard ISO 8601 en appelant toString.

String output = instantHourLater.toString();

Vous voudrez peut-être voir ce moment à travers l'objectif de l' horloge murale d'une région . Ajustez le Instantdans votre fuseau horaire souhaité / prévu en créant un fichier ZonedDateTime.

ZoneId zoneId = ZoneId.of( "America/Montreal" );
ZonedDateTime zdt = ZonedDateTime.ofInstant( instant , zoneId );

Vous pouvez également appeler plusHourspour ajouter votre nombre d'heures. Être zoné signifie que l'heure d'été (DST) et d'autres anomalies seront traitées en votre nom.

ZonedDateTime later = zdt.plusHours( 8 );

Vous devez éviter d'utiliser les anciennes classes date-heure, y compris java.util.Dateet .Calendar. Mais si vous avez vraiment besoin d'une java.util.Dateinteropérabilité avec les classes non encore mises à jour pour les types java.time, convertissez depuis ZonedDateTimevia Instant. De nouvelles méthodes ajoutées aux anciennes classes facilitent la conversion vers / depuis les types java.time.

java.util.Date date = java.util.Date.from( later.toInstant() );

Pour plus d'informations sur la conversion, consultez ma réponse à la question, Convertir java.util.Date en quel type «java.time»? .


À propos de java.time

Le framework java.time est intégré à Java 8 et versions ultérieures. Ces classes supplantent les anciens gênants hérités des classes date-heure tels que java.util.Date, Calendar, &SimpleDateFormat .

Le projet Joda-Time , désormais en mode maintenance , conseille la migration vers les classes java.time .

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

Vous pouvez échanger des objets java.time directement avec votre base de données. Utilisez un pilote JDBC compatible avec JDBC 4.2 ou version ultérieure. Pas besoin de cordes, pas besoin dejava.sql.* classes.

Où obtenir les classes java.time?

  • Java SE 8 , Java SE 9 et versions ultérieures
    • Intégré.
    • Partie de l'API Java standard avec une implémentation groupée.
    • Java 9 ajoute quelques fonctionnalités et corrections mineures.
  • Java SE 6 et Java SE 7
    • Une grande partie de la fonctionnalité java.time est rétroportée vers Java 6 et 7 dans ThreeTen-Backport .
  • Android
    • Versions ultérieures des implémentations de bundle Android des classes java.time.
    • Pour les versions antérieures d'Android (<26), le projet ThreeTenABP adapte ThreeTen-Backport (mentionné ci-dessus). Voir Comment utiliser ThreeTenABP… .

Le projet ThreeTen-Extra étend java.time avec des classes supplémentaires. Ce projet est un terrain d'essai pour d'éventuels futurs ajouts à java.time. Vous trouverez peut - être des classes utiles ici, comme Interval, YearWeek, YearQuarteret plus .


23

Avec Joda-Time

DateTime dt = new DateTime();
DateTime added = dt.plusHours(6);

2
+1 un peu inutile pour cela, mais si vous voulez faire plus de manipulation de date, joda time est une excellente bibliothèque
Joeri Hendrickx

3
@JoeriHendrickx Si le programmeur ajoute des heures à une date, il est très probable qu'il effectue un autre travail de date-heure. Je ne considère pas du tout Joda-Time inutile; la première chose que je fais lors de la mise en place d'un nouveau projet est d'ajouter Joda-Time. Même Sun et Oracle ont convenu que l'ancien java.util.Date & Calendar devait être progressivement supprimé, ils ont donc ajouté le nouveau package java.time. * (Inspiré de Joda-Time) à Java 8.
Basil Bourque

J'ai eu des problèmes avec Joda sur Android. Gardé obtenirClassNotDefinedException
TheRealChx101

23

Depuis Java 8:

LocalDateTime.now().minusHours(1);

Voir LocalDateTimeAPI .


4
Proche mais pas tout à fait raison. Vous devriez opter pour un ZonedDateTimeplutôt que pour un LocalDateTime. Le «Local» signifie non lié à une localité particulière, et non lié à la chronologie. Par exemple, "Noël commence à minuit le 25 décembre 2015" est un moment différent dans les différents fuseaux horaires, sans signification tant que vous n'appliquez pas un fuseau horaire particulier pour obtenir un moment particulier sur la ligne de temps. De plus, sans fuseau horaire, l'heure d'été (DST) et d'autres anomalies ne seront pas traitées avec une telle utilisation de LocalDateTime. Voir ma réponse par comparaison.
Basil Bourque

1
Aussi pour obtenir un java.util.Dateobjet comme le demandeur nous l'avait demandé ZonedDateTime.toInstant()et Date.from()comme décrit ici stackoverflow.com/a/32274725/5661065
hayduke

16

En utilisant la nouvelle classe java.util.concurrent.TimeUnit , vous pouvez le faire comme ceci

    Date oldDate = new Date(); // oldDate == current time
    Date newDate = new Date(oldDate.getTime() + TimeUnit.HOURS.toMillis(2)); // Adds 2 hours

14

Quelque chose comme:

Date oldDate = new Date(); // oldDate == current time
final long hoursInMillis = 60L * 60L * 1000L;
Date newDate = new Date(oldDate().getTime() + 
                        (2L * hoursInMillis)); // Adds 2 hours

1
Pour info, les anciennes classes de date-heure gênantes telles que java.util.Date, java.util.Calendaret java.text.SimpleDateFormatsont maintenant héritées , supplantées par les classes java.time intégrées à Java 8 et Java 9. Voir le didacticiel d'Oracle .
Basil Bourque

7

Ceci est un autre morceau de code lorsque votre Dateobjet est au format Datetime. La beauté de ce code est que si vous donnez plus d'heures, la date sera également mise à jour en conséquence.

    String myString =  "09:00 12/12/2014";
    SimpleDateFormat simpleDateFormat = new SimpleDateFormat("HH:mm dd/MM/yyyy");
    Date myDateTime = null;

    //Parse your string to SimpleDateFormat
    try
      {
        myDateTime = simpleDateFormat.parse(myString);
      }
    catch (ParseException e)
      {
         e.printStackTrace();
      }
    System.out.println("This is the Actual Date:"+myDateTime);
    Calendar cal = new GregorianCalendar();
    cal.setTime(myDateTime);

    //Adding 21 Hours to your Date
    cal.add(Calendar.HOUR_OF_DAY, 21);
    System.out.println("This is Hours Added Date:"+cal.getTime());

Voici la sortie:

    This is the Actual Date:Fri Dec 12 09:00:00 EST 2014
    This is Hours Added Date:Sat Dec 13 06:00:00 EST 2014

1
Vous pouvez également utiliser: Calendar cal = Calendar.getInstance ();
Stefan Sprenger

4
Date argDate = new Date(); //set your date.
String argTime = "09:00"; //9 AM - 24 hour format :- Set your time.
SimpleDateFormat sdf = new SimpleDateFormat("dd-MMM-yyyy");
SimpleDateFormat dateFormat = new SimpleDateFormat("dd-MMM-yyyy HH:mm");
String dateTime = sdf.format(argDate) + " " + argTime;
Date requiredDate = dateFormat.parse(dateTime);

4

Si vous êtes prêt à utiliser java.time, voici une méthode pour ajouter des durées au format ISO 8601:

import java.time.Duration;
import java.time.LocalDateTime;

...

LocalDateTime yourDate = ...

...

// Adds 1 hour to your date.

yourDate = yourDate.plus(Duration.parse("PT1H")); // Java.
// OR
yourDate = yourDate + Duration.parse("PT1H"); // Groovy.  

1
Duration.parse(iso8601duration)est intéressant, merci, mais vous ne pouvez pas utiliser l'opérateur +sur LocalDateTime, vous voudrez peut-être le modifier. Mais .plus(...)ça marche.
qlown

Merci @qlown, je suppose que le + fonctionne de manière groovy parce que c'est comme ça que je l'utilise maintenant. Je modifierai la réponse en conséquence.
Daniel

La question concerne un Dateobjet, qui représente un moment précis en UTC. Votre utilisation de LocalDateTimene répond pas à la question. LocalDateTimen'a aucun concept de fuseau horaire ou de décalage par rapport à UTC et ne peut donc pas représenter un moment. Mauvaise classe pour ce problème. Voir Quelle est la différence entre Instant et LocalDateTime?
Basil Bourque

L' Dateobjet @BasilBourque est obsolète. La question est ambiguë en ce qui concerne le fuseau horaire, donc mes réponses tiennent. De plus, vous pouvez simplement échanger LocalDateTimecontre ZonedDateTime.
Daniel

4

Vous pouvez le faire avec l'API Joda DateTime

DateTime date= new DateTime(dateObj);
date = date.plusHours(1);
dateObj = date.toDate();

Travailler après avoir changé la 1ère ligne en DateTime dateTime = new DateTime (dateObj);
Sundararaj Govindasamy

1

en utilisant les classes Java 8. nous pouvons manipuler la date et l'heure très facilement comme ci-dessous.

LocalDateTime today = LocalDateTime.now();
LocalDateTime minusHours = today.minusHours(24);
LocalDateTime minusMinutes = minusHours.minusMinutes(30);
LocalDate localDate = LocalDate.from(minusMinutes);

La question concerne un Dateobjet, qui représente un moment précis en UTC. Votre utilisation de LocalDateTimene répond pas à la question. LocalDateTimen'a aucun concept de fuseau horaire ou de décalage par rapport à UTC, et ne peut donc pas représenter un moment. Mauvaise classe pour ce problème. Voir Quelle est la différence entre Instant et LocalDateTime?
Basil Bourque

0

Vous pouvez utiliser la classe LocalDateTime de Java 8. Par exemple:

long n = 4;
LocalDateTime localDateTime = LocalDateTime.now();
System.out.println(localDateTime.plusHours(n));

La question concerne un Dateobjet, qui représente un moment précis en UTC. Votre utilisation de LocalDateTimene répond pas à la question. LocalDateTimen'a aucun concept de fuseau horaire ou de décalage par rapport à UTC, et ne peut donc pas représenter un moment. Mauvaise classe pour ce problème. Voir Quelle est la différence entre Instant et LocalDateTime?
Basil Bourque

-1

Vous pouvez utiliser cette méthode, elle est facile à comprendre et à mettre en œuvre:

public static java.util.Date AddingHHMMSSToDate(java.util.Date date, int nombreHeure, int nombreMinute, int nombreSeconde) {
    Calendar calendar = Calendar.getInstance();
    calendar.setTime(date);
    calendar.add(Calendar.HOUR_OF_DAY, nombreHeure);
    calendar.add(Calendar.MINUTE, nombreMinute);
    calendar.add(Calendar.SECOND, nombreSeconde);
    return calendar.getTime();
}

Cette approche est déjà présentée dans une autre réponse publiée il y a des années. Je ne vois pas comment celui-ci ajoute de la valeur.
Basil Bourque

La valeur ajoutée de ma proposition est la simplicité et la facilité de mise en œuvre, il suffit à l'utilisateur de la coller et de l'utiliser et d'ajouter les heures, minutes ou secondes, comme vous le savez, le niveau de Débutant diffère et si les réponses proposées se combinent entre des réponses simples et des réponses avancées ce sera appréciable :)
Nimpo
En utilisant notre site, vous reconnaissez avoir lu et compris notre politique liée aux cookies et notre politique de confidentialité.
Licensed under cc by-sa 3.0 with attribution required.