Не удалось проанализировать DateTimeFormatter с использованием шаблона «ЧЧ: мм Д д МММ ГГГГ» - PullRequest
0 голосов
/ 09 мая 2018

Я получаю дату / время из внешнего источника данных, это возвращается в следующем формате «14:30 сб 05 мая» без года.

Я безуспешно пытался разобрать это в LocalDateTime. Возвращенные данные не возвращают год, так как предполагается, что мы всегда работаем в текущем году.

//date to parse
String time = "14:30 Sat 05 May";

//specify date format matching above string
DateTimeFormatter formatter = DateTimeFormatter.ofPattern("HH:mm E d MMM YYYY") ;

//we do not have a year returned but i can make the assumption we use the current year
LocalDateTime formatDateTime = LocalDateTime.parse(time, formatter).withYear(2018);

Код выше выдает следующее исключение

Исключение в потоке "main" java.time.format.DateTimeParseException: текст '14: 30 сб 05 мая 'не может быть проанализирован с индексом 16

Любая помощь приветствуется.

Ответы [ 2 ]

0 голосов
/ 09 мая 2018

Год по умолчанию

Укажите год по умолчанию в вашем DateTimeFormatter, используя класс DateTimeFormatterBuilder, вызвав parseDefaultingи указав поле года с помощью ChronoField.YEAR.

DateTimeFormatter formatter = new DateTimeFormatterBuilder()
    .appendPattern("HH:mm E d MMM")
    .parseDefaulting(ChronoField.YEAR, 2018)  // <------
    .toFormatter(Locale.ENGLISH);

С этим форматером вместо вашего:

LocalDateTime.parse( "14:30 Sat 05 May" , formatter ) 

… Я получаю:

2018-05-05T14: 30

Обратите внимание, что код запускается в режиме реального времени на IdeOne.com .

Примечания:

  • Ваша строка шаблона формата должна соответствовать концу анализируемой строки-в конец.Поэтому, если в вашей строке даты и времени нет года, не включайте YYYY в шаблон формата.
  • В любом случае не используйте здесь заглавные буквы YYYY.Это для недельного года и полезно только с недельными номерами.Если в вашей строке был год, вы должны были использовать uuuu или строчные буквы yyyy.
  • Сделать привычным указывать явный языковой стандарт для вашего форматера, чтобы вы знали, что он также работает на других компьютерах,и на твоем, когда однажды ты поиграешь с его настройками.
0 голосов
/ 09 мая 2018

LocalDateTime.parse() ожидает String, который представляет действительную дату, которую year часть.
Вы не можете установить год после вызова этого метода следующим образом:

LocalDateTime.parse(time, formatter).withYear(2018);

Год должен быть установлен раньше, потому что в противном случае parse() выдает DateTimeParseException.

В качестве обходного пути вы можете объединить текущий год во входных данных.

Некоторые дополнительные примечания:

  • используемый вами шаблон и введенная дата в текстовом формате не совпадают точно.
  • Вы не указываете Locale для операции разбора.
    Это означает, что он будет работать в соответствии с локальной версией, где работает JVM.
    Чтобы убедиться, что это работает в любом случае, вы должны указать Locale.

Так что вы можете попробовать что-то вроде:

//date to parse
String time = "14:30 Sat 05 May";
time +=  " " + LocalDate.now().getYear();

//specify date format matching above string
DateTimeFormatter formatter = DateTimeFormatter.ofPattern("HH:mm EEE dd MMM yyyy", Locale.US) ;

//we do not have a year returned but i can make the assumption we use the current year
LocalDateTime formatDateTime = LocalDateTime.parse(time, formatter);
...