I want to find the difference in minutes between 2 dates. My code works well if the 2 dates are in the same month(and year) but it seems like the difference considers every month to be 31 days long so for the dates:
2016-02-29 12:21
2016-03-1 12:21
I get 4320 minutes or 72 hours
for:
2016-04-30 12:21
2016-05-01 12:21
I get 2880 minutes or 48 hours
my code where d1 and d2 are Date objects:
long getDateDiff(Date d1, Date d2, TimeUnit timeUnit) {
long diff = d2.getTime() - d1.getTime(); //in millisec
long diffMinutes = TimeUnit.MILLISECONDS.toMinutes(diff);
return diffMinutes;
}
Parse your input strings.
LocalDateTime startLdt = LocalDateTime.parse( "2016-04-30T12:21" ) ;
LocalDateTime stopLdt = LocalDateTime.parse( "2016-05-01T12:21") ;
Assign the time zone or offset-from-UTC intended but omitted from the inputs. I assume you intended UTC itself (an offset of zero).
OffsetDateTime start = startLdt.atOffset( ZoneOffset.UTC );
OffsetDateTime stop = stopLdt.atOffset( ZoneOffset.UTC ) ;
Calculate elapsed time on the scale of days (24-hour chunks of time), hours, minutes, seconds, and nanoseconds.
Duration d = Duration.between( start , stop ) ;
d.toString(): PT24H
Your first example results in 24 hours, as seen when code runs live at IdeOne.com.
Your second example also results in 24 hours, as seen in IdeOne.com.
The Question and other Answers all use the troublesome old date-time classes or the Joda-Time library. Both are supplanted by the java.time classes.
Convert your Date
objects to Instant
objects, the equivalent in java.time. The Instant
class represents a moment on the timeline in UTC with a resolution of nanoseconds (up to nine (9) digits of a decimal fraction).
Instant start = d1.toInstant();
Instant stop = d2.toInstant();
Use Duration
(or Period
) for the span of time in between.
Duration d = Duration.between( start , stop );
Extract the total number of minutes across the entire span-of-time.
long minutes = d.toMinutes() ;
You do not mention the time zone intended for example date-time values. Is their context UTC? Or did you intend some particular time zone. In various time zones, anomalies such as Daylight Saving Time (DST) means days are not always 24 hours long. So time zone is crucial.
Let's look at UTC.
// of(int year, int month, int dayOfMonth, int hour, int minute, int second, int nanoOfSecond, ZoneOffset offset)
OffsetDateTime odtStart1 = OffsetDateTime.of ( 2016 , 2 , 29 , 12 , 21 , 0 , 0 , ZoneOffset.UTC );
OffsetDateTime odtStop1 = OffsetDateTime.of ( 2016 , 3 , 1 , 12 , 21 , 0 , 0 , ZoneOffset.UTC );
Duration d1 = Duration.between ( odtStart1 , odtStop1 );
OffsetDateTime odtStart2 = OffsetDateTime.of ( 2016 , 4 , 30 , 12 , 21 , 0 , 0 , ZoneOffset.UTC );
OffsetDateTime odtStop2 = OffsetDateTime.of ( 2016 , 5 , 1 , 12 , 21 , 0 , 0 , ZoneOffset.UTC );
Duration d2 = Duration.between ( odtStart2 , odtStop2 );
System.out.println ( odtStart1 + "/" + odtStop1 + " = " + d1 );
System.out.println ( odtStart2 + "/" + odtStop2 + " = " + d2 );
2016-02-29T12:21Z/2016-03-01T12:21Z = PT24H
2016-04-30T12:21Z/2016-05-01T12:21Z = PT24H
The string generated by toString
is in standard ISO 8601 format for durations. The P
marks the beginning, the T
separates any years-months-days portion from any hours-minutes-seconds portion.
In both cases the result is twenty-four hours. This is correct because in each case you chose to go from the last day of one month to the first day of the following month. UTC has no anomalies, so we expect exactly 24 hours elapsed.
You can compare the Duration
objects by calling compareTo
. And you can do math to get the difference between them. In this case we expect a different of zero.
Duration difference = d1.minus( d2 );
difference.toString(): PT0S
See this code run live at IdeOne.com.
The java.time framework is built into Java 8 and later. These classes supplant the troublesome old legacy date-time classes such as java.util.Date
, Calendar
, & SimpleDateFormat
.
The Joda-Time project, now in maintenance mode, advises migration to the java.time classes.
To learn more, see the Oracle Tutorial. And search Stack Overflow for many examples and explanations. Specification is JSR 310.
You may exchange java.time objects directly with your database. Use a JDBC driver compliant with JDBC 4.2 or later. No need for strings, no need for java.sql.*
classes.
Where to obtain the java.time classes?
The ThreeTen-Extra project extends java.time with additional classes. This project is a proving ground for possible future additions to java.time. You may find some useful classes here such as Interval
, YearWeek
, YearQuarter
, and more.
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With