Monday, September 13, 2021

How to Format Date to String in Java 8 [Example Tutorial]

One of the common programming tasks in Java is to change the date format of a given Date or String. For example, you have something like "2017-01-18 20:10:00" and you want to convert it that date into "2017-01-18", or you want to convert from dd-MM-YY to MM-dd-YY or to any other format of your choice and need, but a valid date format as per Java specification. How will you do that? Well, it's not that difficult. It's just a two-step process. In the first step, you need to parse String to create an equivalent date using the current format, and then once you got the date, you need to again convert it back to String using the new format. The same process is repeated in both Java 8 and before, only corresponding API and class changes.

If you already know how to convert a date to String then it's pretty easy for you but if you don't know when you need to learn about DateFormat classes like SimpleDateFormat in JDK 6 or 7 and the java.time.format.DateTimeFormatter from the new Date and Time API in JDK 8.

In this article, I'll give you an example of both before and after JDK 8 so that you can change the date format of String in Java 8 or before, but before that let's see what's the difference between SimpleDateFormat and DateTimeFormatter class.

The new Date and Time API has built upon lessons learned from the previous failed attempt at creating a good date, time, and calendar API.  The old API was non-intuitive, not thread-safe, and mutable but the new API has corrected all that mistake.

This means, unlike SimpleDateFormat class, DateTimeFormatter is both thread-safe and immutable, as well easier to use which so many predefined formats. If you are interested to learn more about this API and other interesting Java 8 features I suggest you pick an up-to-date course like The Complete Java MasterClass, which is recently updated to cover the latest Java version.




How to change the format of Date in Java String using JDK 8

You can use the DateTimeFormatter class in JDK 8 to change the date format of String in Java 8. The steps are exactly the same but instead of using SimpleDateFormat and Date class, we'll use the DateTimeFormatter and LocalDateTime class.

The DateTimeFormatter class is used to format and parse the date in Java 8 and LocalDateTime represents a date with time in the local timezone. You can choose the correct class depending on your pattern.

Since we are going to convert the format "yyyy-MM-dd hh:mm:ss" to "yyyy-MM-dd", the LocalDatetime is the right class. If your pattern just contains a date then you can use a LocalDate class instead.

Anyway, here is to JDK 8 code example to change the date format in Java String:

DateTimeFormatter oldPattern = DateTimeFormatter
                                 .ofPattern("yyyy-MM-dd HH:mm:ss");
DateTimeFormatter newPattern = DateTimeFormatter.ofPattern("yyyy-MM-dd");

LocalDateTime datetime = LocalDateTime.parse(input, oldPattern);
String output = datetime.format(newPattern);

You can see exactly the same steps but the code is more robust because DateTimeFormatter is more expressive, thread-safe, and immutable. In general, whenever you use JDK 8, make sure you use the new Date and Time API for all new code you write related to date functionalities.

You should spend sometime to learn the essential classes e.g. LocalDate, LocalTime, LocalDateTime, ZonedDateTime, DateTimeFormatter etc.

Most of the common tasks e.g. converting a string to date and vice-versa, formatting and parsing date, retrieving day, month, year, etc have made simpler. I suggest you join Java SE 8 bootcamp class on Udemy.

How to change date format of String in Java



How to change the date format in a Java String - before JDK 8

If you are not running on JDK 8 then you need to stick with the old date and calendar API. You can use the SimpleDateFormat class to change the date format. Here are the steps you need to follow:

1) Create a Date format with the old pattern

SimpleDateFormat oldFormat = new SimpleDateFormat("yyyy-MM-dd hh:mm:ss");

2) Convert String to Date using the old format as shown below:

Date date = oldFormat.parse(input);

3) Create a DateFormat with the new pattern

SimpleDateFormat newFormat = new SimpleDateFormat("yyyy-MM-dd");

4) Convert Date to String using Dateformatter of the new pattern

String output = newFormat.format(date);

That's it you now have a String in the format you wanted. Though You just need to be a little bit careful while using the SimpleDateFormat class, it's not thread-safe and should not be shared in a multi-threading environment.

You should also be careful with the pattern you specify because letters are case-sensitive, "yyyy-mm-dd" is not the same as "yyyy-MM-dd". The small m is for a minute while capital M is for the month.

Btw, If you think you know the old date and calendar API well, then check out this list of Java date and time interview questions, if you can answer all of them correctly then you are in good shape.





Java Program to convert Date from one format to other

Here is our complete Java program to change the date format of a String in Java or in other words, convert date from one format to another. In this sample, we'll convert date string "2017-01-18 20:10:00" to "2017-01-18" using both old ways like SimpleDateFormat and new way i.e. by using "DateTimeFomatter" class of JDK 8

import java.text.ParseException;
import java.text.SimpleDateFormat;
import java.time.LocalDateTime;
import java.time.format.DateTimeFormatter;
import java.util.Date;

public class Helloworld {

  public static void main(String[] args) throws ParseException {

    String input = "2017-01-18 20:10:00";

    // before Java 8
    SimpleDateFormat oldFormat = new SimpleDateFormat("yyyy-MM-dd hh:mm:ss");
    Date date = oldFormat.parse(input);
    SimpleDateFormat newFormat = new SimpleDateFormat("yyyy-MM-dd");

    String output = newFormat.format(date);

    System.out.println("Date in old format: " + input);
    System.out.println("Date in new format: " + output);

    // Using Java 8 new Date and Time API
    DateTimeFormatter oldPattern = DateTimeFormatter
        .ofPattern("yyyy-MM-dd HH:mm:ss");
    DateTimeFormatter newPattern = DateTimeFormatter.ofPattern("yyyy-MM-dd");

    LocalDateTime datetime = LocalDateTime.parse(input, oldPattern);
    output = datetime.format(newPattern);

    System.out.println("Date in old format (java 8) : " + input);
    System.out.println("Date in new format (java 8) : " + output);

  }

}

Output
Date in old format: 2017-01-18 20:10:00
Date in new format: 2017-01-18
Date in old format (java 8) : 2017-01-18 20:10:00
Date in new format (java 8) : 2017-01-18

You can see we have exactly the same output using both ways. As I told you, the steps are the same just the classes are different. In Java 7 and before, it's SimpleDateFormat and Date class while in Java 8 its DateTimeFormatter and LocalDateTime class.

Btw, If you are not familiar with JDK 8 then The Ultimate Java 8 Tutorial - From beginner to professional is a good place to start with.

How to change date format of String in Java 8



Important points to remember

Converting String to date might look easy but it's not that easy at all. Many Java developer makes subtle mistakes due to the confusing syntax of a specific pattern for date format.

There is also some subtle difference between JDK 8 and before, which means the same pattern which worked with SimpleDateFormat in JDK 8 might not work with DateTimeFormatter, an equivalent class from the new Date and Time API of Java 8. So you got to be a little bit careful while specifying a pattern.

For example, when I first run the program by copying the format from SimpleDateFormat to DateTimeFormatter in the above code, it failed with the following error:

Exception in thread "main" java.time.format.DateTimeParseException:
 Text '2017-01-18 20:10:00' could not be parsed: Invalid value 
for ClockHourOfAmPm (valid values 1 - 12): 20
at java.time.format.DateTimeFormatter.createError(DateTimeFormatter.java:1920)
at java.time.format.DateTimeFormatter.parse(DateTimeFormatter.java:1855)
at java.time.LocalDateTime.parse(LocalDateTime.java:492)
at Helloworld.main(Helloworld.java:28)

The error message is clear, it is expecting 1 to 12 in hour field, so it's expecting an AM/PM date instead of 24 hours format and the reason for that was our pattern, "yyyy-MM-dd hh:mm:ss", which was using small h i.e. "hh" to specify hour of the day.

When I changed this to capital H i.e. "HH" the error goes away. This is a very subtle difference that you might not have noticed while looking at the code.

Another thing that is worth remembering is that capital M i.e. "MM" is used for a month and small m i.e. "mm" is used to specify minutes. Many programmers make this mistake while writing a pattern for date format.

For example, to get the date like 2017-01-18, you need to specify a pattern "dd-MM-yyyy", not "dd-mm-yyyy", which will not work but is easy to type because both dd and yyyy are in the small case.

If you want to learn more about date formatting in Java, I suggest you go through comprehensive Java courses. If you need suggestions, you can check out these best Java online courses from Udemy and Coursera. It covers all essential Java concepts in good detail.


That's all about how to change the date format of a String in Java. We have seen how to do that in both JDK 8 and before. As I said, it's a two-step process, first, you convert String to date using old date format and then convert it back to String using new date format.  

If you are using Java 8, I suggest you use DateTimeFormatter instead of SimpleDateFormat due to obvious reasons. thread-safety and immutability. If you don't know Java 8 yet, you can start your journey from this list of best Java 8 courses, one of the good places to start with.


Other Java 8  and Date Time tutorials You may like

Thanks for reading this article so far. If you like this tutorial then please share it with your friends and colleagues. If you have any questions or feedback then please drop a note.

P. S. - If you are looking for some free courses to learn recent changes on Java 8 and Java 9 then you can also see this list of Free Java 8 and 9 Courses for Programmers.

3 comments:

  1. How can I just formart LocalDate not LocalDateTime

    ReplyDelete
    Replies
    1. Try this:, thanks to Software Engineer :-)

      LocalDate.now().format(DateTimeFormatter.ofPattern("MM/dd/yy"));

      Delete
  2. LocalDate.now().format(DateTimeFormatter.ofPattern("MM/dd/yy"));

    ReplyDelete

Feel free to comment, ask questions if you have any doubt.