No difference, except for the very slight lag caused by allocating a Date object.
From the javadoc the the default constructor of Date
:
Allocates a Date object and initializes it so that it represents the time at which it was allocated, measured to the nearest millisecond.
A Date
is just a thin wrapper around the epoch milliseconds, without any concept of timezones. Only when rendered to a String is timezone considered, but that is handled by the Locale
class.
I will go ahead and post an answer based on my final solution and a sort of summary of the very long comment chain.
To start, the whole conversion chain of:
Date --> Instant --> LocalDateTime --> Do stuff --> Instant --> Date
Is necessary to preserve the time zone information and still do operations on a Date like object that is aware of a Calendar and all of the context therein. Otherwise we run the risk of implicitly converting to the local time zone, and if we try to put it into a human readable date format, the times may have changed because of this.
For example, the toLocalDateTime()
method on the java.sql.Timestamp
class implicitly converts to the default time zone. This was undesirable for my purposes, but is not necessarily bad behavior. It is important, however, to be aware of it. That is the issue with converting directly from a legacy java date object into a LocalDateTime
object. Since legacy objects are generally assumed to be UTC, the conversion uses the local timezone offset.
Now, lets say our program takes the input of 2014-04-16T13:00:00
and save to a database as a java.sql.Timestamp
.
//Parse string into local date. LocalDateTime has no timezone component
LocalDateTime time = LocalDateTime.parse("2014-04-16T13:00:00");
//Convert to Instant with no time zone offset
Instant instant = time.atZone(ZoneOffset.ofHours(0)).toInstant();
//Easy conversion from Instant to the java.sql.Timestamp object
Timestamp timestamp = Timestamp.from(instant);
Now we take a timestamp and add some number of days to it:
Timestamp timestamp = ...
//Convert to LocalDateTime. Use no offset for timezone
LocalDateTime time = LocalDateTime.ofInstant(timestamp.toInstant(), ZoneOffset.ofHours(0));
//Add time. In this case, add one day.
time = time.plus(1, ChronoUnit.DAYS);
//Convert back to instant, again, no time zone offset.
Instant output = time.atZone(ZoneOffset.ofHours(0)).toInstant();
Timestamp savedTimestamp = Timestamp.from(output);
Now we just need to output as a human readable String in the format of ISO_LOCAL_DATE_TIME
.
Timestamp timestamp = ....
LocalDateTime time = LocalDateTime.ofInstant(timestamp.toInstant(), ZoneOffset.ofHours(0));
String formatted = DateTimeFormatter.ISO_LOCAL_DATE_TIME.format(time);
Best Answer
Duration
can only handle fixed-length periods, such as "hours", "minutes", "seconds", "days" (where it assumes exactly 24 hours per day). You can't use "months" withDuration
, because a month varies in length.Period
- the other commonTemporalAmount
implementation - represents years, months and days separately.Personally I would recommend:
plusXxx
method, e.g.time.plusMinutes(10)
. That's about as easy to read as it gets.Period
Duration
Here's an example of where
Period
andDuration
can differ:I wouldn't worry about the efficiency until you really need to - at which point you should have a benchmark so you can test different options.