Différence entre deux dates en Java

Différence entre deux dates en Java

1. Vue d'ensemble

Dans cet article rapide, nous explorerons plusieurs possibilités de calcul de la différence entre deux dates en Java.

Lectures complémentaires:

Incrément Date en Java

Vue d'ensemble des différentes méthodes principales et tierces pour l'ajout de jours à une date

Read more

Vérifier si une chaîne est une date valide en Java

Découvrez différentes manières de vérifier si une chaîne est une date valide en Java.

Read more

2. Core Java

2.1. Utilisation dejava.util.Date pour trouver la différence en jours

Commençons par utiliser les API Java principales pour effectuer le calcul et déterminer le nombre de jours entre les deux dates:

@Test
public void givenTwoDatesBeforeJava8_whenDifferentiating_thenWeGetSix()
  throws ParseException {

    SimpleDateFormat sdf = new SimpleDateFormat("MM/dd/yyyy", Locale.ENGLISH);
    Date firstDate = sdf.parse("06/24/2017");
    Date secondDate = sdf.parse("06/30/2017");

    long diffInMillies = Math.abs(secondDate.getTime() - firstDate.getTime());
    long diff = TimeUnit.DAYS.convert(diffInMillies, TimeUnit.MILLISECONDS);

    assertEquals(diff, 6);
}

2.2. Utilisation dejava.time - Depuis Java 8

Maintenant, calculer la différence est plus intuitif si nous utilisonsLocalDate, LocalDateTime pour représenter les deux dates (avec ou sans temps) en combinaison avecPeriod etDuration:

La différenceLocalDate:

@Test
public void givenTwoDatesInJava8_whenDifferentiating_thenWeGetSix() {
    LocalDate now = LocalDate.now();
    LocalDate sixDaysBehind = now.minusDays(6);

    Period period = Period.between(now, sixDaysBehind);
    int diff = period.getDays();

    assertEquals(diff, 6);
}

Le casLocalDateTime:

@Test
public void givenTwoDateTimesInJava8_whenDifferentiating_thenWeGetSix() {
    LocalDateTime now = LocalDateTime.now();
    LocalDateTime sixMinutesBehind = now.minusMinutes(6);

    Duration duration = Duration.between(now, sixMinutesBehind);
    long diff = Math.abs(duration.toMinutes());

    assertEquals(diff, 6);
}

Here est un peu plus détaillé sur cette API.

2.3. Utilisation dejava.time.temporal.ChronoUnit pour trouver la différence en secondes

L'API de temps dans Java 8 représente une unité de date-heure, par exemple. secondes ou jours, en utilisant l'interface frittéeTemporalUnit . Each unit provides an implementation for a method named between to calculate the amount of time between two temporal objects in terms of that specific unit.

Par exemple, pour calculer les secondes entre deuxLocalDateTimes:

@Test
public void givenTwoDateTimesInJava8_whenDifferentiatingInSeconds_thenWeGetTen() {
    LocalDateTime now = LocalDateTime.now();
    LocalDateTime tenSecondsLater = now.plusSeconds(10);

    long diff = ChronoUnit.SECONDS.between(now, tenSecondsLater);

    assertEquals(diff, 10);
}

ChronoUnit fournit un ensemble d'unités de temps concrètes en implémentant l'interfaceTemporalUnit. It’s highly recommended to static import the ChronoUnit enum values to achieve more readability:

import static java.time.temporal.ChronoUnit.SECONDS;

// omitted
long diff = SECONDS.between(now, tenSecondsLater);

De plus, nous pouvons passer n'importe quel deux objets temporels compatibles à la méthodebetween , même lesZonedDateTime.

Ce qui est génial avecZonedDateTime, c'est que le calcul fonctionnera même s'ils sont définis sur des fuseaux horaires différents:

@Test
public void givenTwoZonedDateTimesInJava8_whenDifferentiating_thenWeGetSix() {
    LocalDateTime ldt = LocalDateTime.now();
    ZonedDateTime now = ldt.atZone(ZoneId.of("America/Montreal"));
    ZonedDateTime sixMinutesBehind = now
      .withZoneSameInstant(ZoneId.of("Asia/Singapore"))
      .minusMinutes(6);

    long diff = ChronoUnit.MINUTES.between(sixMinutesBehind, now);

    assertEquals(diff, 6);
}

2.4. Utilisation dejava.time.temporal.Temporaluntil()

Tout objetTemporal, par exemple LocalDate or ZonedDateTime, provides an until method to calculate the amount of time until another temporal in terms of the specified unit:

@Test
public void givenTwoDateTimesInJava8_whenDifferentiatingInSecondsUsingUntil_thenWeGetTen() {
    LocalDateTime now = LocalDateTime.now();
    LocalDateTime tenSecondsLater = now.plusSeconds(10);

    long diff = now.until(tenSecondsLater, ChronoUnit.SECONDS);

    assertEquals(diff, 10);
}

LesTemporal#until etTemporalUnit#between  sont deux API différentes pour la même fonctionnalité.

3. Bibliothèques externes

3.1. JodaTime

Nous pouvons également faire une implémentation relativement simple avecJodaTime:


    joda-time
    joda-time
    2.9.9

Vous pouvez obtenir la dernière version deJoda-time depuis Maven Central.

CasLocalDate:

@Test
public void givenTwoDatesInJodaTime_whenDifferentiating_thenWeGetSix() {
    LocalDate now = LocalDate.now();
    LocalDate sixDaysBehind = now.minusDays(6);

    Period period = new Period(now, sixDaysBehind);
    long diff = Math.abs(period.getDays());

    assertEquals(diff, 6);
}

De même, avecLocalDateTime c'est:

@Test
public void givenTwoDateTimesInJodaTime_whenDifferentiating_thenWeGetSix() {
    LocalDateTime now = LocalDateTime.now();
    LocalDateTime sixMinutesBehind = now.minusMinutes(6);

    Period period = new Period(now, sixMinutesBehind);
    long diff = Math.abs(period.getDays());
}

3.2. Date4J

Date4j fournit également une implémentation simple et directe, sans noter que, dans ce cas, nous devons fournir explicitement unTimeZone.

Commençons par la dépendance Maven:


    com.darwinsys
    hirondelle-date4j
    1.5.1

Voici un test rapide fonctionnant avec lesDateTime standard:

@Test
public void givenTwoDatesInDate4j_whenDifferentiating_thenWeGetSix() {
    DateTime now = DateTime.now(TimeZone.getDefault());
    DateTime sixDaysBehind = now.minusDays(6);

    long diff = Math.abs(now.numDaysFrom(sixDaysBehind));

    assertEquals(diff, 6);
}

4. Conclusion

Dans ce tutoriel, nous avons illustré quelques manières de calculer la différence entre les dates (avec et sans heure), à ​​la fois en langage Java pur et en utilisant des bibliothèques externes.

Le code source complet de l'article est disponibleover on GitHub.