1. Adding and subtracting dates and time
In programming, working with dates and time is not just about “nicely printing the date on the screen.” Very often you need to:
- find out how many days are left until an important event;
- calculate a user's age;
- determine how much time has passed between two events;
- check whether a deadline has already come;
- add a specific number of days, weeks, months, or hours to a date.
For example, in our app we want to remind the user that there are 3 days left until a task's deadline. Or congratulate them on a recent birthday (if the date is already in the past).
For this, java.time has special classes and methods that make such calculations simple and safe.
Core methods for addition and subtraction
All date and time classes (LocalDate, LocalTime, LocalDateTime, ZonedDateTime, Instant) have methods:
- plusXxx() — add (days, months, years, hours, minutes, etc.)
- minusXxx() — subtract (the same)
import java.time.LocalDate;
LocalDate today = LocalDate.now(); // Today's date
LocalDate tomorrow = today.plusDays(1); // Tomorrow
LocalDate nextMonth = today.plusMonths(1); // In a month
LocalDate lastWeek = today.minusWeeks(1); // A week ago
System.out.println("Today: " + today);
System.out.println("Tomorrow: " + tomorrow);
System.out.println("In a month: " + nextMonth);
System.out.println("A week ago: " + lastWeek);
All these methods return a new object rather than mutating the original. Immutability is everything!
import java.time.LocalTime;
LocalTime now = LocalTime.now();
LocalTime inTwoHours = now.plusHours(2);
LocalTime tenMinutesAgo = now.minusMinutes(10);
System.out.println("Now: " + now);
System.out.println("In 2 hours: " + inTwoHours);
System.out.println("10 minutes ago: " + tenMinutesAgo);
Chained methods
LocalDate vacation = today.plusMonths(2).plusDays(10);
System.out.println("Vacation: " + vacation);
2. Getting the difference between dates: Period and Duration
When you need to know how much time has passed between two dates or instants, two heroes take the stage — Period and Duration. Let's get to know them better.
What is the difference between Period and Duration?
- Period — for working with dates (year, month, day). For example, “3 years, 2 months, and 5 days.”
- Duration — for working with time (hours, minutes, seconds, nanoseconds). For example, “5 hours 30 minutes.”
| Class | Purpose | Usage example |
|---|---|---|
|
Difference between dates | How many years/months/days between dates |
|
Difference between instants | How many hours/minutes/seconds between events |
Example: calculating a user's age
import java.time.LocalDate;
import java.time.Period;
LocalDate birthday = LocalDate.of(2000, 1, 15); // Birthday
LocalDate today = LocalDate.now();
Period age = Period.between(birthday, today);
System.out.println("Age: " + age.getYears() + " years, " +
age.getMonths() + " months, " +
age.getDays() + " days");
Analogy: Period is like the “human” difference between dates (“I am 24 years 5 months 12 days old”).
Example: how much time is left until the deadline
import java.time.LocalDate;
LocalDate deadline = LocalDate.of(2025, 7, 1);
LocalDate today = LocalDate.now();
if (today.isBefore(deadline)) {
Period left = Period.between(today, deadline);
System.out.println("Time left until the deadline: " +
left.getMonths() + " months and " +
left.getDays() + " days");
} else {
System.out.println("The deadline has already passed!");
}
Duration: difference in time
import java.time.LocalDateTime;
import java.time.Duration;
LocalDateTime start = LocalDateTime.of(2025, 6, 1, 10, 0, 0);
LocalDateTime end = LocalDateTime.of(2025, 6, 1, 15, 30, 0);
Duration duration = Duration.between(start, end);
System.out.println("Duration: " + duration.toHours() + " hours " +
(duration.toMinutes() % 60) + " minutes");
Duration measures the difference in seconds, minutes, hours, days (but days are always 24 hours, ignoring calendar specifics).
Comparison: when to use Period vs. Duration?
- If you have dates only (no time) — use Period.
- If you have time (for example, LocalDateTime, Instant) — use Duration.
3. Comparing dates and time: isBefore, isAfter, equals
Sometimes you just need to understand: has a date already arrived or not yet? Is an event in the past or the future? For this, all date and time classes have methods:
- isBefore(otherDate)
- isAfter(otherDate)
- isEqual(otherDate) (or simply equals)
import java.time.LocalDate;
LocalDate today = LocalDate.now();
LocalDate deadline = LocalDate.of(2025, 7, 1);
if (today.isBefore(deadline)) {
System.out.println("There's still time!");
} else if (today.isEqual(deadline)) {
System.out.println("The deadline is today!");
} else {
System.out.println("The deadline has already passed :(");
}
import java.time.LocalTime;
LocalTime now = LocalTime.now();
LocalTime lunch = LocalTime.of(13, 0);
if (now.isAfter(lunch)) {
System.out.println("Lunch is over!");
} else {
System.out.println("There's still time before lunch.");
}
Important: you can compare only objects of the same type (LocalDate with LocalDate, LocalDateTime with LocalDateTime, etc.).
4. Practice: tasks for computing differences and checking deadlines
Example: how many days are left until a task's deadline
import java.time.LocalDate;
import java.time.temporal.ChronoUnit;
LocalDate today = LocalDate.now();
LocalDate deadline = LocalDate.of(2025, 7, 1);
long daysLeft = ChronoUnit.DAYS.between(today, deadline);
if (daysLeft > 0) {
System.out.println("There are " + daysLeft + " days left until the deadline");
} else if (daysLeft == 0) {
System.out.println("The deadline is today!");
} else {
System.out.println("The deadline passed " + Math.abs(daysLeft) + " days ago");
}
ChronoUnit.DAYS.between() is a convenient way to get the exact number of days between two dates (without considering months and years).
Example: how many seconds between two events
import java.time.LocalDateTime;
import java.time.temporal.ChronoUnit;
LocalDateTime start = LocalDateTime.of(2025, 6, 1, 10, 0, 0);
LocalDateTime end = LocalDateTime.of(2025, 6, 1, 15, 30, 0);
long seconds = ChronoUnit.SECONDS.between(start, end);
System.out.println("Between the events, " + seconds + " seconds have passed");
Example: computing a task's age
import java.time.LocalDate;
import java.time.Period;
LocalDate created = LocalDate.of(2025, 5, 20);
LocalDate today = LocalDate.now();
Period period = Period.between(created, today);
System.out.println("The task was created " +
period.getDays() + " days, " +
period.getMonths() + " months, and " +
period.getYears() + " years ago.");
Example: duration between two Instant
import java.time.Instant;
import java.time.Duration;
Instant start = Instant.now();
// ... do something ...
Instant end = Instant.now();
Duration duration = Duration.between(start, end);
System.out.println("Execution took " + duration.toMillis() + " milliseconds");
5. Specifics of using Period and Duration
Period specifics
- Period counts by the calendar: between 28 February and 1 March — 1 day, even if they are in different months.
- You can get the number of years, months, and days separately: getYears(), getMonths(), getDays().
- If you need the total number of days between dates — use ChronoUnit.DAYS.between().
Duration specifics
- Duration works with exact time (hours, minutes, seconds).
- It can work with LocalTime, LocalDateTime, Instant.
- It cannot be used with dates without time (LocalDate) — an exception will be thrown.
Example: difference between Period and Duration
import java.time.LocalDate;
import java.time.LocalDateTime;
import java.time.Duration;
import java.time.Period;
LocalDate date1 = LocalDate.of(2025, 2, 28);
LocalDate date2 = LocalDate.of(2025, 3, 1);
Period period = Period.between(date1, date2); // 2 days (leap year)
long days = java.time.temporal.ChronoUnit.DAYS.between(date1, date2); // 2 days
System.out.println("Period: " + period.getDays() + " days");
System.out.println("ChronoUnit: " + days + " days");
LocalDateTime dt1 = LocalDateTime.of(2025, 6, 1, 23, 0);
LocalDateTime dt2 = LocalDateTime.of(2025, 6, 2, 1, 0);
Duration duration = Duration.between(dt1, dt2); // 2 hours
System.out.println("Duration: " + duration.toHours() + " hours");
6. Using Duration and Period to present the difference in a user-friendly way
When you compute the difference between dates or time for a user, it's not always convenient to display “123456 seconds.” Usually you want something like “2 days 3 hours 15 minutes.”
Example: presenting the difference between dates and time
import java.time.LocalDateTime;
import java.time.Duration;
LocalDateTime start = LocalDateTime.of(2025, 6, 1, 14, 0);
LocalDateTime end = LocalDateTime.of(2025, 6, 3, 16, 30);
Duration duration = Duration.between(start, end);
long days = duration.toDays();
long hours = duration.minusDays(days).toHours();
long minutes = duration.minusDays(days).minusHours(hours).toMinutes();
System.out.println("Difference: " + days + " days " +
hours + " hours " + minutes + " minutes");
7. Considerations when working with ZonedDateTime and Instant
- The difference between two ZonedDateTime values in different zones is calculated by absolute time, not by “human” time in each zone.
- Daylight saving time transitions can affect the hour difference between dates.
Example: difference between ZonedDateTime
import java.time.ZonedDateTime;
import java.time.ZoneId;
import java.time.Duration;
ZonedDateTime MinskTime = ZonedDateTime.of(2025, 6, 1, 12, 0, 0, 0, ZoneId.of("Europe/Minsk"));
ZonedDateTime nyTime = ZonedDateTime.of(2025, 6, 1, 5, 0, 0, 0, ZoneId.of("America/New_York"));
Duration diff = Duration.between(nyTime, MinskTime);
System.out.println("Difference: " + diff.toHours() + " hours");
8. Common mistakes when calculating with dates and time
Mistake #1: Confusing Period and Duration.
If you try to use Duration with LocalDate, you'll get an exception. Use Period for dates, and Duration for time.
Mistake #2: Ignoring time zones.
If you compare dates and time across different time zones, you may get unexpected results. It's better to normalize everything to the same zone or use Instant.
Mistake #3: Expecting plus/minus methods to mutate the object.
All java.time objects are immutable! Don't forget to assign the result to a new variable (for example, today = today.plusDays(1)).
Mistake #4: Using getDays() on Period and thinking it's the total number of days.
In reality, that's only the remaining days after subtracting years and months. For the total number of days, use ChronoUnit.DAYS.between().
Mistake #5: Comparing objects of different types.
The methods isBefore, isAfter, isEqual work only for objects of the same type (for example, LocalDate with LocalDate).
GO TO FULL VERSION