简体   繁体   中英

How to convert format date “MMddhhmmss” to “yyyy-MM-dd HH:mm:ss”?

How to convert calendar date to yyyy-MM-dd HH:mm:ss format.

protected String paymentDatetime (String transmissionDateTime){
    long transactionDateTime = System.currentTimeMillis();
    Date now = new Date();
    SimpleDateFormat sdf = new SimpleDateFormat("yyyy-MM-dd HH:mm:ss");
    try {
        SimpleDateFormat df = new SimpleDateFormat("MMddhhmmss");
        Calendar nowDate = Calendar.getInstance();
        nowDate.setTime(now);

        Calendar transmissionDate = Calendar.getInstance();
        transmissionDate.setTime(df.parse(transmissionDateTime));
        transmissionDate.set(Calendar.YEAR, nowDate.get(Calendar.YEAR));

        transactionDateTime = transmissionDate.getTime().getTime();
    } catch (ParseException e) {
        LOGGER.error("cannot parse transmission date time : " + transmissionDateTime);
    }
    return sdf.format(transactionDateTime);
}

I want to get the value thrown by String transmissionDateTime , but in fact when I throw the value = 1707 1255 17 (in AM) will be convert to "2020-07-17 00:55:17". How to convert so that every 12.00 or 00.00 (12 o'clock) both AM and PM don't change?

Do not handle dates and times as strings in your program. Handle and store them as proper date-time objects. When you take string input, parse it to a date-time object. Only when you need to give string output, format your date-time object into an appropriate string.

java.time

I think that your parsing becomes clearer with java.time, the modern Java date and time API. I understand that the hour given in the string is hour of day, so 00 means 12 midnight and 12 means 12 noon.

    Year thisYear = Year.now(ZoneId.systemDefault());
    DateTimeFormatter inputFormatter = new DateTimeFormatterBuilder()
            .appendPattern("ddMMHHmmss")
            .parseDefaulting(ChronoField.YEAR, thisYear.getValue())
            .toFormatter();
    
    String transmissionDateTimeString = "1707125517";
    
    LocalDateTime transmissionDateTime
            = LocalDateTime.parse(transmissionDateTimeString, inputFormatter);
    
    System.out.println(transmissionDateTime);

Output when running today:

2020-07-17T12:55:17

Formatting output

I am showing you two options for formatting output as 2020-07-17 12:55:17 .

  1. Use a formatter
  2. Simply replace the T with a space

Use a formatter:

    DateTimeFormatter outputFormatter = DateTimeFormatter.ofPattern("uuuu-MM-dd HH:mm:ss");
    String output = transmissionDateTime.format(outputFormatter);

Simply replace the T :

    String output = transmissionDateTime.toString().replace('T', ' ');

What went wrong in your code?

Lower case hh in a format pattern string is for hour within AM or PM from 01 through 12. This goes for both the old-fashioned SimpleDateFormat and for the modern DateTimeFormatter . You didn't tell the formatter whether you wanted AM or PM. In this case SimpleDateFormat assumes AM, which is why you got a time og 00:55:17. Upper case HH is for hour of day from 00 through 23.

It furthermore seems that you have accidentally swapped month and day of month in your format pattern for parsing, MMddhhmmss . When I called your method, I got 2020-05-07 00:55:17 . Month and day of month are wrong. Your df parsed 1707125517 into Fri May 07 00:55:17 CET 1971 . There is no 17th month of the year, but SimpleDateFormat confusingly extrapolates, so the 17th month of 1970 becomes the 5th month of 1971.

Links

Calendar and SimpleDateFormat are old classes and no longer recommended.
Use the LocalDateTime and DateTimeFormatter classes in the java.time package.

DateTimeFormatter from = DateTimeFormatter.ofPattern("MMddhhmmss");
DateTimeFormatter to12Hour = DateTimeFormatter.ofPattern("yyyy-MM-dd hh:mm:ss a");
DateTimeFormatter to24Hour = DateTimeFormatter.ofPattern("yyyy-MM-dd HH:mm:ss");
LocalDateTime ldt = LocalDateTime.now();
System.out.println(ldt.format(from));
System.out.println(ldt.format(to12Hour));
System.out.println(ldt.format(to24Hour));

Prints

0716082236
2020-07-16 08:22:36 PM
2020-07-16 20:22:36

As already covered by a comment : MMddhhmmss should be MMddHHmmss using uppercase HH .


String "1707125517" with format MMddHHmmss means MM = 17 and dd = 07 . When parsed without a year, the year defaults to 1970, and month 17 of the year 1970 resolves to month 5 of the year 1971, which is why the question code results in 2020-05-07 (month 5, day 7).

Are you sure the input with Month = 17 is what you want to parse, and that the format pattern is what you intended? Seems that month and day are flipped, given you said "will be convert to "2020-07-17 00:55:17"" , where month is 7 and day is 17, so perhaps you should try format ddMMHHmmss instead .

The method in the question can be shortened to use only one Calendar object instead of two:

protected static String paymentDatetime(String dateTime) {
    Calendar cal = Calendar.getInstance();
    int year = cal.get(Calendar.YEAR);
    try {
        cal.setTime(new SimpleDateFormat("ddMMHHmmss").parse(dateTime));
    } catch (ParseException e) {
        throw new IllegalArgumentException("Invalid date string: " + dateTime, e);
    }
    cal.set(Calendar.YEAR, year);
    return new SimpleDateFormat("yyyy-MM-dd HH:mm:ss").format(cal.getTime());
}

The method was also changed to not ignore parsing exception .


The old antiquated Date and SimpleDateFormat classes should not be used. Instead, use the newer Java 8 Time API classes.

protected static String paymentDatetime(String dateTime) {
    DateTimeFormatter in = new DateTimeFormatterBuilder()
            .appendPattern("ddMMHHmmss")
            .parseDefaulting(ChronoField.YEAR, Year.now().getValue())
            .toFormatter();
    DateTimeFormatter out = DateTimeFormatter.ofPattern("uuuu-MM-dd HH:mm:ss");
    return LocalDateTime.parse(dateTime, in).format(out);
}

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM