6

I'm trying to parse a string to a date, this is what I have:

SimpleDateFormat sdf = new SimpleDateFormat("EEE MMM dd yyyy HH:mm:ss zZ (zzzz)");
Date date = new Date();
try {
    date = sdf.parse(time);
} catch (ParseException e) {
    e.printStackTrace();
}

the string to parse is this:

Sun Jul 15 2012 12:22:00 GMT+0300 (FLE Daylight Time)

I followed the http://docs.oracle.com/javase/7/docs/api/java/text/SimpleDateFormat.html

Pretty sure I've done everything by the book. But it is giving me ParseException.

java.text.ParseException: Unparseable date: 
"Sun Jul 15 2012 12:22:00 GMT+0300 (FLE Daylight Time)"

What am I doing wrong? Patterns I Have tried:

EEE MMM dd yyyy HH:mm:ss zzz
EEE MMM dd yyyy HH:mm:ss zZ (zzzz)
Eric Leschinski
  • 146,994
  • 96
  • 417
  • 335
Jaanus
  • 16,161
  • 49
  • 147
  • 202

5 Answers5

11

You seem to be mixing the patterns for z and Z. If you ignore the (FLE Daylight Time), since this is the same info as in GMT+0300, the problem becomes that SimpleDateFormat wants either GMT +0300 or GMT+03:00. The last variant can be parsed like this:

String time = "Sun Jul 15 2012 12:22:00 GMT+03:00 (FLE Daylight Time)";
SimpleDateFormat sdf = new SimpleDateFormat("EEE MMM dd yyyy HH:mm:ss zzz");
Date date = sdf.parse(time);

[EDIT]
In light of the other posts about their time strings working, this is probably because your time string contains conflicting information or mixed formats.

Keppil
  • 45,603
  • 8
  • 97
  • 119
  • You need to add the `:` to your time string for this to work. – Keppil Jul 12 '12 at 07:40
  • are you sure since ... using : `EEE MMM dd yyyy HH:mm:ss zzz`, and when I print it out : ` Date date = new Date(); ` , and then show the format : `System.out.println(sdf.format(date));` , it prints : `Thu Jul 12 2012 10:47:09 EEST` – Jaanus Jul 12 '12 at 07:47
  • Actually I did this, and it worked ... `time = time.substring(0, 31) + ":" + time.substring(31);` . seems very weird, no easier way lol? – Jaanus Jul 12 '12 at 07:50
  • Like I said, it seems your `time` String is using mixed formats in an unfortunate way that causes trouble for `SimpleDateFormat`, so if you have any way to generate that in a more friendly pattern, that would certainly help. – Keppil Jul 12 '12 at 07:53
  • Problem comes because of diff timezones GMT or EEET, so I just reduced it to only what I need. until minutes and seconds. `time = time.substring(0, 21);` – Jaanus Jul 12 '12 at 07:54
2

java.time

I should like to contribute the modern answer. Use java.time, the modern Java date and time API, for your date and time work.

First define a formatter for parsing:

private static final DateTimeFormatter PARSER = DateTimeFormatter
        .ofPattern("EEE MMM dd yyyy HH:mm:ss 'GMT'Z (", Locale.ROOT);

Then parse in this way:

    String time = "Sun Jul 15 2012 12:22:00 GMT+0300 (FLE Daylight Time)";
    
    TemporalAccessor parsed = PARSER.parse(time, new ParsePosition(0));
    OffsetDateTime dateTime = OffsetDateTime.from(parsed);
    
    System.out.println(dateTime);

Output is:

2012-07-15T12:22+03:00

I am not parsing your entire string, but enough to establish a point in time and an offset from GMT (or UTC). Java cannot parse the time zone name FLE Daylight Time. This is a Microsoft invention that Java does not know. So I parse up to the round bracket before FLE in order to validate this much of the string. To instruct the DateTimeFormatter that it needs not parse the entire string I use the overloaded parse method that takes a ParsePosition as second argument.

From Wikipedia:

Sometimes, due to its use on Microsoft Windows, FLE Standard Time (for Finland, Lithuania, Estonia, or sometimes Finland, Latvia, Estonia) … are used to refer to Eastern European Time.

If you indispensably need a Date object, typically for a legacy API that you cannot afford to upgrade to java.time just now, convert like this:

    Date oldfashionedDate = Date.from(dateTime.toInstant());
    System.out.println(oldfashionedDate);

Output when run in Europe/Tallinn time zone:

Sun Jul 15 12:22:00 EEST 2012

What went wrong in your code?

Your SimpleDateFormat successfully parsed GMT+03 into a “time zone” matching the small z in the format pattern string. It then tried to parse the remaining 00 into an offset to match the capital Z. Since an offset requires a sign, this failed.

What am I doing wrong?

As others have said, you should not try to parse GMT into a time zone abbreviation. GMT can be used as a time zone abbreviation; but your time is not in GMT. So you don’t want that. It would only be misleading. Had you been successful, you would rather have risked an incorrect result because you had parsed a time zone that was incorrect for your purpose.

Links

Ole V.V.
  • 81,772
  • 15
  • 137
  • 161
1

Try it this way..

System.out.println(new SimpleDateFormat(
                "EEE MMM dd yyyy HH:mm:ss zZ (zzzz)").format(new Date()));

Output i got:

Thu Jul 12 2012 12:41:35 IST+0530 (India Standard Time)
Kumar Vivek Mitra
  • 33,294
  • 6
  • 48
  • 75
1

You can try to print the date format string :

/**
 * @param args
 */
public static void main(String[] args) {
    SimpleDateFormat sdf = new SimpleDateFormat(
            "EEE MMM dd yyyy HH:mm:ss zZ (zzzz)");
    Date date = new Date();
    try {
        //
        System.out.println(sdf.format(date));
        date = sdf.parse(time);
    } catch (Exception e) {
        e.printStackTrace();
    }
}
Jason
  • 1,241
  • 8
  • 16
  • It is using my language, wtf, I want it to use english. `N Juuli 12 2012 10:18 EEST+0300 (Eastern European Summer Time)` – Jaanus Jul 12 '12 at 07:18
1

If you have problems with locales, you can either set the default Locale for the whole application

Locale.setDefault(Locale.ENGLISH);

or just use the english locale on your SimpleDateFormat

SimpleDateFormat sdf = new SimpleDateFormat("EEE MMM dd yyyy HH:mm:ss zZ (zzzz)", Locale.ENGLISH);

You can also use Locale.US or Locale.UK.

brimborium
  • 9,362
  • 9
  • 48
  • 76