Tyler DeWitt Tyler DeWitt - 10 months ago 49
Java Question

Java Unparsable date

I have a string with the format:

String dateString = "2014-03-17T20:05:49.2300963Z"

Trying this:

SimpleDateFormat df = new SimpleDateFormat("yyyy-MM-dd'T'kk:mm:ss.SSSX");
Date date = df.parse(dateString);

Results in an
Unparsable date

The docs: http://docs.oracle.com/javase/7/docs/api/java/text/SimpleDateFormat.html indicate that
is used with
ISO 8601
when a single letter is used for the TimeZone.

Re-reading the docs, I've switched up the
a little:

SimpleDateFormat df = new SimpleDateFormat("yyyy-MM-dd'T'HH:mm:ss.SSS");
dateString = dateString.replace("Z", "");

I take out the
because I know the timezone, use
instead of
and add a couple more
for giggles.

Now the time is parsing, but incorrectly. Date is accurate, Time seems to be random.

The problem is that java only allows millisecond accuracy, so
is being interpreted as 2300 seconds and 963 milliseconds. I'll need to format my string a little differently to get this to work.

Turns out you can't have a fractional part of a second in Java. It has to be truncated to milliseconds. I ended up using a type made available to me by my database, but the general solution is to truncate the fractional part of the second to millisecond. I'll post example code of how to do that as an answer.

Answer Source

How to truncate the fractional seconds to milliseconds (because Java can't handle fractional seconds):

public String truncate(String dateString){
  int numberOfDigits = dateString.substring(dateString.indexOf("."), dateString.length() - 1).length();

  String justMilliSecondsDate = null;
  if (numberOfDigits == 3) {
    justMicrosDate = dateString;
  else if (numberOfDigits > 3) {
    justMilliSecondsDate = dateString.substring(0, dateString.length() - numberOfDigits + 3);
  else {
      justMilliSecondsDate = dateString;
      for (int i = numberOfDigits ; i < 3 ; i++) justMilliSecondsDate += "0";

  return justMilliSecondsDate;