Java LocalDate expliqué : guide complet de la gestion des dates en Java 8 et versions ultérieures

目次

Qu’est-ce que LocalDate ?

La gestion des dates en Java a beaucoup évolué depuis la version 8. Au centre de cette évolution se trouve LocalDate. LocalDate est un objet immuable qui représente uniquement une date (année, mois et jour, par ex. 2025-06-26), sans aucun concept de temps ou de fuseau horaire. Il vous permet de gérer la date d’aujourd’hui ou des dates calendaires spécifiques de manière simple et sûre.

Différences par rapport aux classes de dates legacy

Avant Java 8, des classes telles que java.util.Date et java.util.Calendar étaient couramment utilisées. Cependant, ces classes présentaient plusieurs problèmes, notamment un design sujet aux erreurs (comme les mois basés sur zéro), un manque de sécurité pour les threads, et des API non intuitives. En conséquence, elles menaient souvent à des bugs ou à des comportements inattendus.

LocalDate résout ces problèmes et offre les fonctionnalités suivantes :

  • Gestion explicite uniquement de l’année, du mois et du jour (par ex. 26 juin 2025)
  • Objet immuable (les valeurs ne peuvent pas être modifiées, assurant la sécurité)
  • Noms de méthodes intuitifs et conception d’API (par ex. plusDays(1) pour le jour suivant, getMonthValue() pour le numéro du mois)
  • Indépendant des fuseaux horaires (comportement cohérent indépendamment des paramètres du système ou du serveur)

Quand utiliser LocalDate ?

LocalDate est idéal lorsque vous souhaitez gérer les dates de manière claire, n’avez pas besoin d’informations sur l’heure, et voulez implémenter des opérations sur les dates de façon sûre et facile. Les cas d’utilisation typiques incluent :

  • Enregistrement de dates sans heure, comme les anniversaires ou les dates commémoratives
  • Gestion des plannings, des délais et des dates d’échéance
  • Calcul des délais ou des jours restants

Pour ces raisons, LocalDate peut être considéré comme la nouvelle norme pour la gestion des dates en Java. Dans la section suivante, nous expliquerons en détail l’utilisation de base et l’initialisation de LocalDate.

Opérations de base avec LocalDate

LocalDate fournit une API intuitive et simple pour la manipulation des dates. Cette section explique les fonctionnalités couramment utilisées avec des exemples concrets.

Obtenir la date actuelle

Pour obtenir la date d’aujourd’hui, utilisez la méthode LocalDate.now(). Elle retourne la date système actuelle (indépendante du fuseau horaire) sous forme d’instance LocalDate.

import java.time.LocalDate;

LocalDate today = LocalDate.now();
System.out.println(today); // Example: 2025-06-26

Créer une date spécifique

Pour créer une date arbitraire dans le passé ou le futur, utilisez LocalDate.of(int year, int month, int dayOfMonth). Cela vous permet de créer librement des dates telles que le 31 décembre 2024.

LocalDate specialDay = LocalDate.of(2024, 12, 31);
System.out.println(specialDay); // 2024-12-31

Analyser une date à partir d’une chaîne

Pour générer un LocalDate à partir d’une chaîne comme « 2023-03-15 », utilisez la méthode LocalDate.parse(String text). Si la chaîne suit le format ISO standard (« YYYY-MM-DD »), aucune configuration supplémentaire n’est requise.

LocalDate parsedDate = LocalDate.parse("2023-03-15");
System.out.println(parsedDate); // 2023-03-15

Analyse avec un format personnalisé (Supplément)

Si vous devez gérer des dates dans un format personnalisé tel que « 2023/03/15 », vous pouvez combiner DateTimeFormatter avec parse().

import java.time.format.DateTimeFormatter;

DateTimeFormatter formatter = DateTimeFormatter.ofPattern("yyyy/MM/dd");
LocalDate formattedDate = LocalDate.parse("2023/03/15", formatter);
System.out.println(formattedDate); // 2023-03-15

Comme montré ci-dessus, les opérations de base de LocalDate sont intuitives et directes. Dans le code Java moderne, l’initialisation et la conversion des dates sont rarement sources de confusion. Dans le chapitre suivant, nous expliquerons comment extraire les valeurs d’année, de mois, de jour et de jour de la semaine à partir de LocalDate.

Récupération de l’année, du mois, du jour et du jour de la semaine

LocalDate vous permet d’extraire facilement non seulement la date elle-même, mais aussi les composants individuels tels que l’année, le mois, le jour et le jour de la semaine. Cette section explique comment récupérer ces éléments couramment utilisés.

Obtenir l’année, le mois et le jour

Pour récupérer chaque composant d’une instance LocalDate, utilisez les méthodes getter dédiées.

LocalDate date = LocalDate.of(2025, 6, 26);

int year = date.getYear();           // Year (e.g. 2025)
int month = date.getMonthValue();    // Month as a number (1–12, e.g. 6)
int day = date.getDayOfMonth();      // Day of month (1–31, e.g. 26)

System.out.println("Year: " + year);
System.out.println("Month: " + month);
System.out.println("Day: " + day);

Obtenir les noms des mois et des jours de la semaine

LocalDate prend également en charge la récupération des noms des mois et des jours de la semaine, ce qui est utile lorsque vous avez besoin de représentations textuelles.

  • Nom du mois (représentation en anglais) L’utilisation de getMonth() renvoie une valeur d’énumération Month (par exemple, JUNE).
    import java.time.Month;
    
    Month monthName = date.getMonth(); // JUNE (uppercase English)
    System.out.println(monthName);
    
  • Nom du jour de la semaine getDayOfWeek() renvoie une énumération DayOfWeek (par exemple, THURSDAY).
    import java.time.DayOfWeek;
    
    DayOfWeek dayOfWeek = date.getDayOfWeek(); // THURSDAY (uppercase English)
    System.out.println(dayOfWeek);
    

Affichage des noms des mois et des jours de la semaine en japonais

Si vous souhaitez afficher les noms des mois ou des jours de la semaine en japonais plutôt qu’en anglais, vous pouvez personnaliser la sortie à l’aide de DateTimeFormatter.

import java.time.format.DateTimeFormatter;
import java.util.Locale;

DateTimeFormatter formatter =
    DateTimeFormatter.ofPattern("yyyy年MM月dd日(E)", Locale.JAPANESE);
String formatted = date.format(formatter); // 2025年06月26日(木)
System.out.println(formatted);

Résumé des composants récupérés

L’un des principaux atouts de LocalDate est qu’il vous permet de récupérer l’année, le mois, le jour et le jour de la semaine à l’aide de méthodes intuitives. Cette flexibilité facilite grandement la gestion des dates dans les applications métier et web.

Calculs de dates (addition et soustraction)

Les calculs de dates tels que l’ajout ou la soustraction de jours sont fréquemment requis pour la gestion des horaires et les calculs d’échéances. Avec LocalDate, vous pouvez effectuer en toute sécurité et de manière intuitive des opérations comme « trois jours plus tard », « une semaine plus tôt » ou « la différence entre deux dates ».

Ajout de dates

  • Ajout de jours
    LocalDate today = LocalDate.of(2025, 6, 26);
    LocalDate threeDaysLater = today.plusDays(3); // Three days later
    System.out.println(threeDaysLater); // 2025-06-29
    
  • Ajout de mois ou d’années
    LocalDate nextMonth = today.plusMonths(1); // One month later
    LocalDate nextYear = today.plusYears(1);   // One year later
    System.out.println(nextMonth); // 2025-07-26
    System.out.println(nextYear);  // 2026-06-26
    

Soustraction de dates

  • Soustraction de jours, de mois ou d’années
    LocalDate lastWeek = today.minusWeeks(1);   // One week earlier
    LocalDate previousDay = today.minusDays(1); // Previous day
    System.out.println(lastWeek);    // 2025-06-19
    System.out.println(previousDay); // 2025-06-25
    

Calcul des différences entre dates

  • Calcul de la différence en jours
    import java.time.temporal.ChronoUnit;
    
    LocalDate start = LocalDate.of(2025, 6, 1);
    LocalDate end = LocalDate.of(2025, 6, 26);
    
    long daysBetween = ChronoUnit.DAYS.between(start, end); // 25
    System.out.println(daysBetween); // 25
    
  • Calcul des différences en utilisant d’autres unités (mois, années)
    long monthsBetween = ChronoUnit.MONTHS.between(start, end); // 0
    long yearsBetween = ChronoUnit.YEARS.between(start, end);   // 0
    

Résumé

En utilisant les méthodes d’addition et de soustraction de LocalDate, vous pouvez facilement implémenter des calculs de dates courants tels que « l’échéance du mois prochain » ou « les jours écoulés depuis le dernier événement ».

Comme LocalDate est immuable, l’instance originale n’est jamais modifiée. Chaque opération renvoie une nouvelle instance LocalDate, garantissant une gestion sécurisée des dates.

Opérations avancées : Ajustement de dates spécifiques

Dans la gestion réelle des dates, une simple addition ou soustraction n’est souvent pas suffisante. Les exigences courantes incluent la détermination du « dernier jour du mois » ou du « premier jour du mois suivant ». LocalDate fournit des API pratiques pour ces types d’ajustements.

Utilisation de TemporalAdjuster

Avec LocalDate, vous pouvez combiner la méthode with() et TemporalAdjuster pour effectuer des opérations intuitives telles que « fin du mois », « début du mois » ou « prochain jour de la semaine spécifique ». Des ajusteurs intégrés sont fournis dans la classe TemporalAdjusters.

Obtenir le premier et le dernier jour d’un mois

  • Obtenir le dernier jour du mois
    import java.time.LocalDate;
    import java.time.temporal.TemporalAdjusters;
    
    LocalDate date = LocalDate.of(2025, 6, 26);
    LocalDate endOfMonth = date.with(TemporalAdjusters.lastDayOfMonth());
    System.out.println(endOfMonth); // 2025-06-30
    
  • Obtenir le premier jour du mois
    LocalDate startOfMonth = date.with(TemporalAdjusters.firstDayOfMonth());
    System.out.println(startOfMonth); // 2025-06-01
    

Ajustement en fonction des jours de la semaine

Les ajustements basés sur les jours de la semaine — comme « le deuxième lundi du mois » ou « le vendredi suivant » — sont également faciles à implémenter.

  • Obtenir le vendredi suivant
    import java.time.DayOfWeek;
    
    LocalDate nextFriday =
        date.with(TemporalAdjusters.next(DayOfWeek.FRIDAY));
    System.out.println(nextFriday); // 2025-06-27
    
  • Obtenir le deuxième lundi du mois en cours
    LocalDate secondMonday =
        date.with(TemporalAdjusters.dayOfWeekInMonth(2, DayOfWeek.MONDAY));
    System.out.println(secondMonday); // 2025-06-09
    

Ajustement au début ou à la fin d’une année

Vous pouvez appliquer la même approche pour récupérer le premier ou le dernier jour d’une année.

LocalDate startOfYear =
    date.with(TemporalAdjusters.firstDayOfYear());
LocalDate endOfYear =
    date.with(TemporalAdjusters.lastDayOfYear());

System.out.println(startOfYear); // 2025-01-01
System.out.println(endOfYear);   // 2025-12-31

Création d’ajusteurs personnalisés

Si vous avez besoin d’une logique d’ajustement de date personnalisée basée sur des règles métier spécifiques, vous pouvez implémenter vous-même l’interface TemporalAdjuster.

En combinant LocalDate avec TemporalAdjusters, même les calculs de dates complexes deviennent intuitifs et flexibles. Cela est particulièrement utile lors de la gestion des échéances ou des calendriers spécifiques à l’entreprise.

Travailler avec LocalDate et LocalDateTime

Dans l’API Date et Heure de Java (package java.time), LocalDate représente uniquement une date, tandis que LocalDateTime représente à la fois la date et l’heure. En pratique, les développeurs ont souvent besoin de convertir entre ces deux types. Cette section explique comment effectuer ces conversions.

Conversion de LocalDate en LocalDateTime

Pour ajouter des informations d’heure à un LocalDate et le convertir en LocalDateTime, utilisez atTime() ou atStartOfDay().

  • Ajouter une heure spécifique
    import java.time.LocalDate;
    import java.time.LocalDateTime;
    
    LocalDate date = LocalDate.of(2025, 6, 26);
    LocalDateTime dateTime =
        date.atTime(14, 30, 0); // 2025-06-26 14:30:00
    System.out.println(dateTime);
    
  • Créer un LocalDateTime au début de la journée
    LocalDateTime startOfDay =
        date.atStartOfDay(); // 2025-06-26T00:00
    System.out.println(startOfDay);
    

Conversion de LocalDateTime en LocalDate

Pour extraire uniquement la partie date d’un LocalDateTime, utilisez la méthode toLocalDate().

import java.time.LocalDateTime;

LocalDateTime dateTime =
    LocalDateTime.of(2025, 6, 26, 14, 30);
LocalDate dateOnly = dateTime.toLocalDate();
System.out.println(dateOnly); // 2025-06-26

Combinaison de LocalDate avec LocalTime

Vous pouvez également combiner un LocalDate et un LocalTime pour créer un LocalDateTime.

import java.time.LocalTime;

LocalTime time = LocalTime.of(9, 0);
LocalDateTime combined =
    date.atTime(time); // 2025-06-26T09:00
System.out.println(combined);

Résumé

  • Convertir LocalDate en LocalDateTime en utilisant atTime() ou atStartOfDay()
  • Convertir LocalDateTime en LocalDate en utilisant toLocalDate()
  • Séparer et combiner la date et l’heure est courant dans les systèmes réels

Gestion des exceptions et bonnes pratiques

La gestion des dates peut facilement entraîner des exceptions inattendues si des valeurs ou des formats invalides sont utilisés. Même en travaillant avec LocalDate, des exceptions peuvent survenir en raison de dates inexistantes ou d’erreurs de parsing. Cette section explique les exceptions courantes et les meilleures pratiques pour les gérer en toute sécurité.

Spécifier une Date Inexistante

Si vous essayez de créer une date qui n’existe pas — comme le 30 février 2023 — une DateTimeException sera levée.

import java.time.LocalDate;

// Example that throws an exception
LocalDate invalidDate = LocalDate.of(2023, 2, 30);

Dans de tels cas, il est important d’attraper l’exception et de la gérer de manière appropriée.

try {
    LocalDate invalidDate = LocalDate.of(2023, 2, 30);
} catch (DateTimeException e) {
    System.out.println("An invalid date was specified: " + e.getMessage());
}

Exceptions Lors du Parsing de Chaînes

Lors de l’utilisation de LocalDate.parse(), une DateTimeParseException est levée si le format de la chaîne est invalide ou si la date elle-même n’existe pas.

import java.time.format.DateTimeParseException;

try {
    LocalDate date = LocalDate.parse("2023/02/30");
} catch (DateTimeParseException e) {
    System.out.println("Failed to parse date: " + e.getMessage());
}

Meilleures Pratiques

  • Valider les valeurs d’entrée à l’avance Lors de l’acceptation d’une entrée utilisateur, validez à la fois le format et la valeur avant le parsing pour éviter les exceptions.
  • Attraper les exceptions et fournir des messages conviviaux pour l’utilisateur Au lieu de laisser l’application planter, retournez des messages d’erreur clairs et compréhensibles à l’utilisateur.
  • Tirer parti de l’immutabilité Parce que LocalDate est immutable, traitez toujours les résultats de calcul comme de nouvelles instances plutôt que de les écraser sur les existantes.

Pièges Courants

  • Gestion du 29 février dans les années bissextiles
  • Spécifier des valeurs en dehors des plages valides (par exemple, mois = 13, jour = 0)
  • Formats non correspondants lors du parsing de chaînes

Ces problèmes sont particulièrement courants chez les débutants, donc une attention particulière est requise.

Cas d’Utilisation Pratiques pour LocalDate

LocalDate ne se limite pas au stockage simple de dates — il est largement utilisé dans les systèmes et applications métier du monde réel. Voici plusieurs exemples pratiques.

Calcul d’Anniversaire et d’Âge

Calculer l’âge d’une personne en se basant sur sa date de naissance est un cas d’utilisation classique. Utiliser LocalDate avec Period rend cela facile.

import java.time.LocalDate;
import java.time.Period;

LocalDate birthDay = LocalDate.of(1990, 8, 15);
LocalDate today = LocalDate.now();

Period period = Period.between(birthDay, today);
int age = period.getYears();
System.out.println("Age: " + age);

Gestion des Dates Limites et d’Échéance

LocalDate est également utile pour les systèmes de gestion de tâches, comme le calcul du nombre de jours restants jusqu’à une date limite.

LocalDate deadline = LocalDate.of(2025, 7, 10);
long daysLeft =
    java.time.temporal.ChronoUnit.DAYS.between(today, deadline);

System.out.println("Days remaining until deadline: " + daysLeft);

Planification et Génération de Calendrier

Des exigences telles que « une réunion le deuxième lundi de chaque mois » peuvent être implémentées facilement en utilisant TemporalAdjusters.

import java.time.DayOfWeek;
import java.time.temporal.TemporalAdjusters;

LocalDate secondMonday =
    LocalDate.of(2025, 7, 1)
        .with(TemporalAdjusters.dayOfWeekInMonth(2, DayOfWeek.MONDAY));

System.out.println("Second Monday of July: " + secondMonday);

Validation de Dates dans les Systèmes Web et APIs

LocalDate est fréquemment utilisé dans les systèmes backend pour valider les entrées de dates. Par exemple, vous pourriez vouloir rejeter les dates futures ou les dates plus anciennes qu’une certaine plage.

LocalDate inputDate = LocalDate.parse("2024-12-31");
LocalDate tenYearsAgo = today.minusYears(10);

.if (inputDate.isAfter(today)) {
    System.out.println("Les dates futures ne sont pas autorisées");
} else if (inputDate.isBefore(tenYearsAgo)) {
    System.out.println("Veuillez spécifier une date dans les 10 dernières années");
} else {
    System.out.println("La date est valide");
}

Adoption in Training and Production Systems

As seen in many competing articles, LocalDate is now a standard topic in Java training programs and onboarding curricula. It is also widely used in production systems such as banking business-day calculations and inventory management.

FAQ (Frequently Asked Questions)

Q1. What is the difference between LocalDate and Date?

A.
LocalDate is part of the modern Java Date and Time API introduced in Java 8 and represents only a date (year, month, day). java.util.Date, on the other hand, is a legacy class that includes time and internally manages values in milliseconds.

LocalDate is immutable, intuitive, and thread-safe, and is recommended for modern Java development.

Q2. Can LocalDate handle time zones?

A.
LocalDate itself does not contain time zone information. If time zone support is required, use ZonedDateTime or OffsetDateTime. A common approach is to manage dates with LocalDate first, then convert when time zones become necessary.

Q3. What is the difference between LocalDate and LocalDateTime?

A.
LocalDate represents only a date. LocalDateTime represents both date and time (e.g. 2025-06-26 14:00). Use LocalDate for deadlines or anniversaries, and LocalDateTime for events with precise timestamps.

Q4. Can I parse custom date formats?

A.
Yes. By using DateTimeFormatter, you can parse dates in custom formats.

import java.time.format.DateTimeFormatter;

DateTimeFormatter formatter =
    DateTimeFormatter.ofPattern("yyyy/MM/dd");
LocalDate date =
    LocalDate.parse("2025/06/26", formatter);

Q5. How should I handle invalid dates or formats?

A.
Invalid dates or formats cause exceptions such as DateTimeException or DateTimeParseException. Use try-catch blocks, validate input in advance, and provide clear error messages to users.

Q6. Can I compare two LocalDate instances?

A.
Yes. Use isAfter(), isBefore(), or isEqual().

LocalDate date1 = LocalDate.of(2025, 6, 26);
LocalDate date2 = LocalDate.of(2025, 7, 1);

if (date1.isBefore(date2)) {
    System.out.println("date1 est antérieure à date2");
}

Conclusion

This article provided a comprehensive explanation of Java LocalDate, from basic concepts to advanced use cases. Key points include:

  • What LocalDate is An immutable date-only object introduced in Java 8 that fixes the flaws of legacy Date and Calendar classes.
  • Basic usage Retrieving the current date, creating specific dates, and parsing strings using simple APIs.
  • Extracting components Easily retrieving year, month, day, and weekday values.
  • Date calculations Intuitive addition, subtraction, and difference calculations.
  • Date adjustments Using TemporalAdjusters to handle end-of-month, weekdays, and more.
  • Integration with time APIs Flexible conversion between LocalDate, LocalDateTime, and LocalTime.
  • Safe handling and best practices Proper exception handling and validation for robust systems.
  • Real-world applications and FAQs Practical examples such as age calculation, deadlines, scheduling, and validation.

Next Steps

Once you master LocalDate, date handling becomes straightforward and reliable. For more advanced scenarios—such as time zones, period calculations, and formatting—consider learning ZonedDateTime, Period, and DateTimeFormatter.

Use LocalDate as a powerful foundation to build clean, robust, and maintainable Java applications.