I want my String "10:10" to be converted into time in a format of hh:mm instead of MM/dd/yyyy hh:mm:ss aa
Date date;
SimpleDateFormat sdf;
sdf = new SimpleDateFormat("hh:mm");
try
{
date = sdf.parse(a.getString("time").toString());
Log.d(TAG, "onCreate: "+date);
Log.d(TAG, "onCreate: "+a.getString("time"));
}
catch (ParseException e) {
e.printStackTrace();
}
But i am getting this in my logcat
D/MTAG: onCreate: Thu Jan 01 10:00:00 GMT+05:00 1970
D/MTAG: onCreate: 10:00
String timeString = "10:10";
LocalTime time = LocalTime.parse(timeString);
System.out.println(time);
This prints
10:10
I am cheating a bit, though. The way I read your question, you asked for a date-time object with the format HH:mm in it. Neither a LocalTime object (used in the above snippet) nor a Date (used in your code) can have a format in it. What you get when you concatenate the Date to a string or print the LocalTime is the result of the object’s toString method, and you cannot change this method (only in subclasses, and you don’t want that). In other words, when you want a specific format, you need to have that format in a string outside the date-time object.
The lucky part is that LocalTime.toString() produces the format you want (as long as the seconds and fraction of second are zero; otherwise they would be in the string too).
Will that work on your Android device? It will. LocalTime is a class of JSR-310 also known as java.time, the modern Java date and time API introduced nearly 4 years ago, early in 2014. JSR-310 has been backported to Java 6 and 7 in ThreeTen Backport, which in turn has been adapted to Android in ThreeTenABP. So get ThreeTenABP, add it to your project and start enjoying how much nicer it is to work with than the outdated date and time classes.
PS There’s a bug in your format pattern string in the question: Lowercase hh is for hour within AM or PM from 1 through 12, which works nicely when the hours are 10, but not always. I am convinced that you want uppercase HH for hour of day in the interval 0 through 23. When I run your code with a string of 12:12, I get Thu Jan 01 00:12:00 CET 1970. The hours are 0, not 12.
Links
Oracle tutorial: Date Time, explaining how to use java.time.
ThreeTen Backport project
ThreeTenABP, Android edition of ThreeTen Backport
Question: How to use ThreeTenABP in Android Project, with a very thorough explanation.
Java Specification Request (JSR) 310, where the modern date and time API was first described.
Date and time formats are specified by date and time pattern strings.
Within date and time pattern strings, unquoted letters from 'A' to 'Z'
and from 'a' to 'z' are interpreted as pattern letters representing
the components of a date or time string. Text can be quoted using
single quotes (') to avoid interpretation. "''" represents a single
quote. All other characters are not interpreted; they're simply copied
into the output string during formatting or matched against the input
string during parsing.
Read Document
Try this:
DateFormat aFormatter = new SimpleDateFormat("HH:mm");
Date dt = aFormatter.parse("10:10");
Calendar aCalander = Calendar.getInstance();
aCalander.setTime(dt);
int hour = aCalander.get(Calendar.HOUR);
int minute = aCalander.get(Calendar.MINUTE);
When a Date is created, it will be in the format of "Thu Jan 01 10:00:00 GMT+05:00 1970" as you mention in your output. So if you want to display and play around with the format of the date you should use the format method in SimpleDateFormat. I hope the below code help you understand better.
//formatting date in Java using SimpleDateFormat
String date_s = "10:10";
SimpleDateFormat dt = new SimpleDateFormat("hh:mm");
Date date = dt.parse(date_s);
System.out.println(date);
System.out.println(dt.format(date));
Related
I want to convert the date in string to date object being the string "10h 57m 20s October 13 2020". How can be done? may replace firstly the h, m and s to get the format "10:57:20 October 13 2020"? As well, I tried the last format "10:57:20 October 13 2020" to get the date with DateTimeFormat and DateTimeFormatterBuilder() but is does not work with the month or it works but the hour coverts to 00:00:00.
Thanks
java.time
I recommend that you use java.time, the modern Java date and time API, for your date and time work. Like Joop Eggen already wrote, put the letters that are part of your format in single quotes in the format pattern string:
private static final DateTimeFormatter FORMATTER
= DateTimeFormatter.ofPattern("H'h' m'm' s's' MMMM d y", Locale.ENGLISH);
This will allow you to parse like this:
String dateInString = "10h 57m 20s October 13 2020";
LocalDateTime dateTime = LocalDateTime.parse(dateInString, FORMATTER);
System.out.println(dateTime);
Output:
2020-10-13T10:57:20
You shouldn’t take any interest in the old-fashioned Date class. However, sometimes we need to pass a Date to a legacy API not yet upgraded to java.time. The conversion requires that we know the time zone assumed for the parsed date and time. For example:
ZoneId zone = ZoneId.of("America/Tegucigalpa");
Instant i = dateTime.atZone(zone).toInstant();
Date oldfashionedDate = Date.from(i);
System.out.println(oldfashionedDate);
Example output:
Tue Oct 13 10:57:20 CST 2020
Tutorial link
Oracle tutorial: Date Time explaining how to use java.time.
You can place fixed letters in apostrophes.
"HH'h' mm'm' ss's' MMMM dd yyyy"
Furthermore hh is the 12 hour format to be combined wiht a AM/PM.
HH is the 24 hour format.
Also the locale must be correct, maybe explicitly set. Here English.
I am struggling with this ..
I have an input string - like this: 2021-10-13 11:33:16.000-04
Using Java.
I need to get a Date object from it.
which formatting pattern can I use ?
I try with these
SimpleDateFormat inFormatter = new SimpleDateFormat ("yyyy-MM-dd HH:mm:ss.SSS'-'ZZ");
and
SimpleDateFormat inFormatter = new SimpleDateFormat ("yyyy-MM-dd HH:mm:ss.SSSZZ");
and I keep getting
java.text.ParseException: Unparseable date: "2021-10-13 11:33:16.000-04"
at java.base/java.text.DateFormat.parse(DateFormat.java:396)
at com.dima.tests.DatesConversions.main(DatesConversions.java:24)
Please, help !!
Don't use Date as it is outdated. Use the classes in the java.time
OffsetDateTime odt = OffsetDateTime.parse(str,
DateTimeFormatter.ofPattern("yyyy-MM-dd HH:mm:ss.SSSX"));
System.out.println(odt);
Prints
2021-10-13T11:33:16-04:00
java.time
Even though you need to give an old-fashionede Date object to a legacy API beyond your control, I still recommend that you use java.time, the modern Java date and time API, in your own code. The final conversion to Date is pretty straight-forward.
I’d use this formatter for maximum reuse of existing formatters:
private static final DateTimeFormatter PARSER = new DateTimeFormatterBuilder()
.append(DateTimeFormatter.ISO_LOCAL_DATE)
.appendLiteral(' ')
.append(DateTimeFormatter.ISO_LOCAL_TIME)
.appendOffset("+HHmm", "+00")
.toFormatter(Locale.ROOT);
Then we parse and convert like this:
String input = "2021-10-13 11:33:16.000-04";
OffsetDateTime dateTime = OffsetDateTime.parse(input, PARSER);
System.out.println(dateTime);
Instant i = dateTime.toInstant();
Date oldfashionedDate = Date.from(i);
System.out.println(oldfashionedDate);
Output in my time zone, Europe/Copenhagen:
2021-10-13T11:33:16-04:00
Wed Oct 13 17:33:16 CEST 2021
Denmark is at offset +02:00 at this time of year, so 6 hours ahead of the UTC offset -04 from your string. Therefore Date.toString() confusingly prints a clock hour that is 6 hours ahead of the original time of day.
Note: if your forward service accepts anything else than an old-fashioned Date, you should not be using that class. For example, if a String is required, the OffsetDateTime that we got can be formatted into a new string using a second DateTimeFormatter (or in lucky cases, its toString method).
What went wrong in your code?
First, a UTC offset can have positive or negative sign. Instead of -04 you could have had for example +09. Formatters are designed for to take the sign, + or -, as part of the offset. Therefore hardcoding the minus sign as a literal, as in your first attempt, is bound to fail. In your second attempt, yyyy-MM-dd HH:mm:ss.SSSZZ, you are already closer. However, ZZ is for an offset with sign and four digits (like +0530 or -0400; hour and minute), so does not work for a two-digit offset like -04. Your SimpleDateFormat expected more digits where your string ended and therefore threw the exception that you saw.
Link
Oracle tutorial: Date Time explaining how to use java.time.
Since you are using ISO 8601 time zone timezone, you have the use the below pattern.
SimpleDateFormat inFormatter = new SimpleDateFormat("yyyy-MM-dd HH:mm:ss.SSSX");
And then, to get the date:
Date date = inFormatter.parse("2021-10-13 11:33:16.000-04");
Always check the documentation.
I read many posts at SO and tested most of them. None of them is working for me. Here is my code:
DateTimeZone fromTimeZone = DateTimeZone.forID("America/New_York");
DateTimeZone toTimeZone = DateTimeZone.forID("US/Central");
Date now = new Date();
DateTime dateTime = new DateTime(now, fromTimeZone);
DateTime newDateTime = dateTime.withZone(toTimeZone);
System.out.println(dateTime.toDate() + "--" + newDateTime.toDate());
Here is what I got in print:
Tue Aug 22 13:08:13 EDT 2017--Tue Aug 22 13:08:13 EDT 2017
I am hoping to display "Tue Aug 22 12:08:13 CDT 2017" for the second time zone.
A java.util.Date doesn't have timezone information. Joda's DateTime has, but it's wrapped into a Chronology to translate this instant to "human readable" date/time fields.
But in the end, both objects just represent points (instants) in the time-line.
Just check the values of dateTime.getMillis(), newDateTime.getMillis(), dateTime.toDate().getTime() and newDateTime.toDate().getTime(). They will all be exactly the same, and this value represents the number of milliseconds since epoch (1970-01-01T00:00Z).
The timezone passed to the DateTime object just affects the output of toString() (when this milliseconds value is "translated" to a local date and time), but it doesn't change the milliseconds value itself. So if you do:
DateTime dateTime = new DateTime(now, fromTimeZone);
System.out.println(dateTime);
It will print the date and time that's equivalent to the milliseconds value, but converted to the fromTimeZone (America/New_York):
2017-08-22T13:33:08.345-04:00
The withZone method just sets to a different timezone, but keeps the same milliseconds value:
DateTime newDateTime = dateTime.withZone(toTimeZone);
System.out.println(newDateTime);
The code above keeps the instant (the milliseconds value), but prints the equivalent date and time in the toTimeZone (US/Central):
2017-08-22T12:33:08.345-05:00
The .toDate() method returns a java.util.Date, which just contains the same milliseconds value, and no timezone information. Then, System.out.println implicity calls Date::toString() method, and this converts the milliseconds value to the JVM's default timezone. In this case both will be:
Tue Aug 22 13:33:08 EDT 2017
Because both dates represent the same instant (the same number of milliseconds since epoch).
If you want to get a String that contains the date in a specific format, you can use a org.joda.time.format.DateTimeFormatter:
DateTimeFormatter fmt = DateTimeFormat.forPattern("EEE MMM dd HH:mm:ss z yyyy").withLocale(Locale.ENGLISH);
System.out.println(fmt.print(new DateTime(DateTimeZone.forID("US/Central"))));
There's no need to convert dates objects, because actually no conversion is really happening: all methods above don't change the milliseconds value.
Also note that I used a java.util.Locale to make sure the month and day of week are in English. If you don't specify a locale, the JVM default will be used, and it's not guaranteed to always be English (and it can also be changed, even at runtime, so it's better to always specify it).
Then I get the current date and set the timezone to be used when printing it. Note that you can get a DateTime directly, there's no need to create a java.util.Date.
The output will be:
Tue Aug 22 12:33:08 CDT 2017
To get exactly the same output you want (with both dates), you can do:
DateTimeFormatter fmt = DateTimeFormat.forPattern("EEE MMM dd HH:mm:ss z yyyy").withLocale(Locale.ENGLISH);
DateTime nowNy = new DateTime(DateTimeZone.forID("America/New_York"));
DateTime nowCentral = nowNy.withZone(DateTimeZone.forID("US/Central"));
System.out.println(fmt.print(nowNy) + "--" + fmt.print(nowCentral));
The output will be:
Tue Aug 22 13:33:08 EDT 2017--Tue Aug 22 12:33:08 CDT 2017
Java new Date/Time API
Joda-Time is in maintainance mode and being replaced by the new APIs, so I don't recommend start a new project with it. Even in joda's website it says: "Note that Joda-Time is considered to be a largely “finished” project. No major enhancements are planned. If using Java SE 8, please migrate to java.time (JSR-310)." (if you don't want to or can't migrate from Joda to another API, you can desconsider this section).
If you're using Java 8, consider using the new java.time API. It's easier, less bugged and less error-prone than the old APIs.
If you're using Java <= 7, you can use the ThreeTen Backport, a great backport for Java 8's new date/time classes. And for Android, there's the ThreeTenABP (more on how to use it here).
The code below works for both.
The only difference is the package names (in Java 8 is java.time and in ThreeTen Backport (or Android's ThreeTenABP) is org.threeten.bp), but the classes and methods names are the same.
The relevant classes are DateTimeFormatter (to format the date to a String in a specific format), ZonedDateTime (which represents a date and time in a specific timezone) and a ZoneId (which represents a timezone):
// formatter - use English locale for month and day of week
DateTimeFormatter fmt = DateTimeFormatter.ofPattern("EEE MMM dd HH:mm:ss z yyyy", Locale.ENGLISH);
// current date/time in New York timezone
ZonedDateTime nowNy = ZonedDateTime.now(ZoneId.of("America/New_York"));
// convert to another timezone (US/Central)
ZonedDateTime nowCentral = nowNy.withZoneSameInstant(ZoneId.of("US/Central"));
// format dates
System.out.println(fmt.format(nowNy) + "--" + fmt.format(nowCentral));
The output is the same as above.
I am doing this to set a date format and then convert it into date datatype but it is not giving expected results.
SimpleDateFormat dateFormat = new SimpleDateFormat("yyyy/MM/dd");
DateFormat formatter = new SimpleDateFormat("yyyy/MM/dd");
String cur_date=dateFormat.format(new Date());
myDb.setDOB(formatter.parse(cur_date));
Scenario is: I want current date to be converted in yyyy/mm/dd and then pass it in setDOB(Date date).
EDIT:Result added Result is Tue Jan 01 00:08:00 IST 2013
GUYS! I am not using 'mm',here I just mistakenly wrote mm in DateFormat it is also MM
EDIT AGAIN First I just used setDOB(new Date() ); but got formatting issue,
then I used SimpleDateFormat.format to set yyyy/MM/dd but it returns String so used
DateFormat.parse to convert it back into date type.
You're not using the same format. Case matters! "MM" is for months, "mm" is for minutes.
The issue is you MM in the format.
SimpleDateFormat dateFormat = new SimpleDateFormat("yyyy/MM/dd");
DateFormat formatter = new SimpleDateFormat("yyyy/mm/dd");
MM is month
mm is minute
Refer here for the detailed formats. So it should have been,
SimpleDateFormat dateFormat = new SimpleDateFormat("yyyy/MM/dd");
DateFormat formatter = new SimpleDateFormat("yyyy/MM/dd");
+1 mael for spotting the format issue first, however...
Date is a container for the number of milliseconds since the epoch (Jan-1970-01-01 GMT), it does not care about the format of the values.
For example, the following...
SimpleDateFormat dateFormat = new SimpleDateFormat("yyyy/MM/dd");
DateFormat formatter = new SimpleDateFormat("yyyy/MM/dd");
Date now = new Date();
String cur_date = dateFormat.format(now);
try {
System.out.println("Now = " + now);
System.out.println("cur_date = " + cur_date);
System.out.println("dateFormat.parse(cur_date) = " + dateFormat.parse(cur_date));
} catch (ParseException exp) {
exp.printStackTrace();
}
Outputs...
Now = Thu Aug 01 18:08:39 EST 2013
cur_date = 2013/08/01
dateFormat.parse(cur_date) = Thu Aug 01 00:00:00 EST 2013
So you can lose important data about the date by doing this...
Leave formatting to when you want to display the value, not when you want to store it (if you can get away with it)
It sounds like you're expecting a Date to "know" its format. It doesn't. A Date object just contains a number of milliseconds since the Unix epoch. It doesn't know about time zones, or calendars, or string formats. It's just a date.
So your code should just be:
myDb.setDOB(new Date());
... and then handle the formatting of that wherever you're displaying it.
You re using different date String patterns. MM is for months, mm is for minutes (see SimpleDateFormat API)
Your setDOB is taking a Date object. I fail to see why you might want to format your date when giving it is as a parameter in your method call. Usually one formats a date when it needs to be rendered / stored somewhere.
formatter.parse is used to parse the String Date, It returns Date Object.
The date is represented as a Date object or as the milliseconds as example since January 1, 1970, 00:00:00 GMT.
I am not getting what actually your doing. Date object is always represented as in the above format.
The Question and other Answers all use troublesome old date-time classes that are now legacy, supplanted by the java.time classes.
LocalDate
Apparently you want a date-only value.
The LocalDate class represents a date-only value without time-of-day and without time zone.
A time zone is crucial in determining a date. For any given moment, the date varies around the globe by zone. For example, a few minutes after midnight in Paris France is a new day while still “yesterday” in Montréal Québec.
Specify a proper time zone name in the format of continent/region, such as America/Montreal, Africa/Casablanca, or Pacific/Auckland. Never use the 3-4 letter abbreviation such as EST or IST as they are not true time zones, not standardized, and not even unique(!).
ZoneId z = ZoneId.of( "America/Montreal" ); // Or "Asia/Kolkata" , "Pacific/Auckland" , etc.
LocalDate today = LocalDate.now( z );
Generating strings
To generate a string representing the value of that LocalDate, simply call toString(). That method generates a string in standard ISO 8601 format.
String output = today.toString();
2017-01-23
Your desired format is close to that, using slash characters in place of hyphens. I suggest sticking with the standard formats whenever possible. But if you insist, just replace the characters.
String output = today.toString().replace( "-" , "/" );
For other formats use the DateTimeFormatter class. And be aware of that class’ ability to automatically localize while generating a string.
About java.time
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.
Where to obtain the java.time classes?
Java SE 8, Java SE 9, and later
Built-in.
Part of the standard Java API with a bundled implementation.
Java 9 adds some minor features and fixes.
Java SE 6 and Java SE 7
Much of the java.time functionality is back-ported to Java 6 & 7 in ThreeTen-Backport.
Android
Later versions of Android bundle implementations of the java.time classes.
For earlier Android, the ThreeTenABP project adapts ThreeTen-Backport (mentioned above). See How to use ThreeTenABP….
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.
I have an extensive DATE-TIME conversion class, but i came across a scenario that i cannot resolve:
I have a java.util.date: Tue May 10 00:00:00 BST 2011
I have a java.sql.time: 03:58:44
I need to create a java.util.date: Tue May 10 03:58:44 BST 2011
The only approach i came up with is:
public static Date getDate(Date date, Time time) {
Calendar calendar=Calendar.getInstance();
calendar.set(date.getYear(), date.getMonth(), date.getDay(), time.getHours(), time.getMinutes(), time.getSeconds());
return calendar.getTime();
}
Totally deprecated code, and does not work:
java.lang.IllegalArgumentException at java.sql.Time.getYear(Unknown Source)
Any ideas?
java.sql.Time is just a wrapper over the java.util.Date. You can use it as if you would add two java.util.Date objects.
For example, set Calendar to java.sql.Time:
calendar.setTime(time);
Now extract the hour/minute/seconds fields, i.e.:
calendar.get(Calendar.HOUR);
Next, set the Calendar to java.util.Date object and add these three fields to its time, i.e.:
calendar.add(Calendar.HOUR, hour);
And get the Date back:
calendar.getTime();
Easiest way would be to just add the milli secs together to create a new date, ala
public static Date getDate(Date date, Time time) {
return new Date(date.getTime() + time.getTime())
}
vickirk's solution wasn't so bad, but has timezone issues, which results in the one hour less you observed.
I suppose, BST means British Summer Time, which is GMT +0100. Now, java.util.Date and its descendants internally work with numbers of milliseconds since midnight Jan 01, 1970 GMT. The timezone is not taken into account until you stringfy the date/time with toString(). And they use your local timezone for that, which is BST, apparently. That means, what is really stored in these objects, is
java.util.date: Mon May 09 23:00:00 GMT 2011
java.sql.time: 02:58:44 GMT
When you add the internal values (which are retrieved by getTime()) like vickirk suggested, you obtain a date which contains
Tue May 10 01:58:44 GMT 2011, which then results in
Tue May 10 02:58:44 BST 2011 on stringification.
So the explanation for the one hour less is that the timezone offset applies twice, when you stringified the values separately, whereas it applies only once after the addition, because you stringfy only once now. Or, from another point of view, adding the internal value of the point in time 03:58:44 BST is equivalent to adding a time span of 2h 58m 44s.
So to get a time span of 3h 58m 44s encoded in a java.sql.Time, you have to make up for the time zone offset manually. You do that by parsing the time string "00:00:00" with java.sql.Time, which will result in an internal value of -3600000 which is equivalent to 31 Dec 1969 23:00:00 GMT, i.e. one hour before the epoch. This is the negative of the time zone offset.
public static Date mergeDate(Date date, Time time) {
long tzoffset = -(Time.valueOf("00:00:00").getTime());
return new Date(date.getTime() + time.getTime() + tzoffset);
}
Of course, all this is a dirty hack, which is necessary because you insist on interpreting the Time's value as a time span, while it really is a point in time.
Instead, you can use this.
public static Date getDate(Date date, Time time) {
Calendar calendar=Calendar.getInstance();
calendar.setTimeZone(TimeZone.getTimeZone("UTC"));
calendar.setTime(date);
calendar.add(Calendar.MILLISECOND, (int) time.getTime());
return calendar.getTime();
}
Can you do
java.util.Date newDate = new java.util.Date(sqlDate.getTime());
try these
public static Date getDate(Date date, Time time) {
Calendar calendar=Calendar.getInstance();
calendar.setTime(date);
Calendar calendar1=Calendar.getInstance();
calendar1.setTime(time);
calendar.set(Calendar.MINUTE, calendar1.get(Calendar.MINUTE));
calendar.set(Calendar.SECOND, calendar1.get(Calendar.SECOND));
calendar.set(Calendar.HOUR_OF_DAY, calendar1.get(Calendar.HOUR_OF_DAY));
return calendar.getTime();
}
I recommend that you use java.time, the modern Java date and time API, for your date and time work. If you cannot avoid getting the date as a java.util.Date (a class that doesn’t represent a date) and your time of day as a java.sql.Time, convert both to modern types and combine them from there.
Java 8 and later
// Time zone to use throughout
ZoneId zone = ZoneId.systemDefault();
// Initialize values to be used for demonstration
Instant startOfDay = LocalDate.of(2011, Month.MAY, 10)
.atStartOfDay(zone)
.toInstant();
Date date = Date.from(startOfDay);
Time time = Time.valueOf(LocalTime.of(3, 58, 44));
// Do work
LocalTime localTime = time.toLocalTime();
LocalDateTime combination = date.toInstant()
.atZone(zone)
.toLocalDate()
.atTime(localTime);
// Print result
System.out.println(combination);
Output:
2011-05-10T03:58:44
Only if you indispensably need a Date, typically for a legacy API that you cannot afford to upgrade to java.time just now, convert back:
Instant inZone = combination.atZone(zone).toInstant();
Date oldfashionedDate = Date.from(inZone);
System.out.println(oldfashionedDate);
In my time zone the output is:
Tue May 10 03:58:44 CEST 2011
Java 6 and 7
For Java 6 and 7 use the backport of java.time, ThreeTen Backport (links at the botton). For the backport we need to use DateTimeUtils for converting to modern types:
LocalTime localTime = DateTimeUtils.toLocalTime(time);
LocalDateTime combination = DateTimeUtils.toInstant(date)
.atZone(zone)
.toLocalDate()
.atTime(localTime);
Output is the same as before. Also if you need to convert back to a Date, use DateTimeUtils:
Instant inZone = combination.atZone(zone).toInstant();
Date oldfashionedDate = DateTimeUtils.toDate(inZone);
Again output is the same as before.
Links
Oracle tutorial: Date Time explaining how to use java.time.
Java Specification Request (JSR) 310, where java.time was first described.
ThreeTen Backport project, the backport of java.time to Java 6 and 7 (ThreeTen for JSR-310).
Java 8+ APIs available through desugaring
ThreeTenABP, Android edition of ThreeTen Backport
Question: How to use ThreeTenABP in Android Project, with a very thorough explanation.