Це важкий шлях, і ці java.util.Date
методи встановлення застаріли з часу Java 1.1 (1997). Просто відформатуйте дату за SimpleDateFormat
допомогою шаблону формату, який відповідає вхідному рядку .
У вашому конкретному випадку "2 січня 2010 року" як вхідного рядка:
- "Січень" - це місяць з повним текстом, тому використовуйте для цього
MMMM
шаблон
- "2" - короткий день місяця, тому використовуйте для цього
d
шаблон.
- "2010" - це чотиризначний рік, тому використовуйте для цього
yyyy
шаблон.
String string = "January 2, 2010";
DateFormat format = new SimpleDateFormat("MMMM d, yyyy", Locale.ENGLISH);
Date date = format.parse(string);
System.out.println(date); // Sat Jan 02 00:00:00 GMT 2010
Зауважте важливість явного Locale
аргументу. Якщо ви його опустите, то він буде використовувати локаль за замовчуванням, який не обов'язково є англійською мовою, як використовується у назві місяця вхідного рядка. Якщо локал не збігається з вхідним рядком, то ви блудно отримаєте java.text.ParseException
рівний, навіть коли шаблон формату здається дійсним.
Ось витяг релевантності з javadoc з переліком усіх доступних моделей формату:
Letter Date or Time Component Presentation Examples
------ ---------------------- ------------------ -------------------------------------
G Era designator Text AD
y Year Year 1996; 96
Y Week year Year 2009; 09
M/L Month in year Month July; Jul; 07
w Week in year Number 27
W Week in month Number 2
D Day in year Number 189
d Day in month Number 10
F Day of week in month Number 2
E Day in week Text Tuesday; Tue
u Day number of week Number 1
a Am/pm marker Text PM
H Hour in day (0-23) Number 0
k Hour in day (1-24) Number 24
K Hour in am/pm (0-11) Number 0
h Hour in am/pm (1-12) Number 12
m Minute in hour Number 30
s Second in minute Number 55
S Millisecond Number 978
z Time zone General time zone Pacific Standard Time; PST; GMT-08:00
Z Time zone RFC 822 time zone -0800
X Time zone ISO 8601 time zone -08; -0800; -08:00
Зауважте, що шаблони залежать від регістру і що текстові візерунки з чотирьох або більше символів представляють повну форму в іншому випадку використовується коротка або скорочена форма, якщо вона є. Так, наприклад, MMMMM
або більше це не потрібно.
Ось кілька прикладів дійсних SimpleDateFormat
шаблонів для розбору даного рядка на сьогоднішній день:
Input string Pattern
------------------------------------ ----------------------------
2001.07.04 AD at 12:08:56 PDT yyyy.MM.dd G 'at' HH:mm:ss z
Wed, Jul 4, '01 EEE, MMM d, ''yy
12:08 PM h:mm a
12 o'clock PM, Pacific Daylight Time hh 'o''clock' a, zzzz
0:08 PM, PDT K:mm a, z
02001.July.04 AD 12:08 PM yyyyy.MMMM.dd GGG hh:mm aaa
Wed, 4 Jul 2001 12:08:56 -0700 EEE, d MMM yyyy HH:mm:ss Z
010704120856-0700 yyMMddHHmmssZ
2001-07-04T12:08:56.235-0700 yyyy-MM-dd'T'HH:mm:ss.SSSZ
2001-07-04T12:08:56.235-07:00 yyyy-MM-dd'T'HH:mm:ss.SSSXXX
2001-W27-3 YYYY-'W'ww-u
Важливо відзначити, що SimpleDateFormat
це НЕ поточно. Іншими словами, ви ніколи не повинні оголошувати і призначати його як статичну або змінну екземпляра, а потім використовувати його повторно з різних методів / потоків. Ви завжди повинні створювати його абсолютно новим у локальній області методу.
Оновлення Java 8
Якщо вам трапляється на Java 8 або новішої версії, скористайтеся DateTimeFormatter
(також тут натисніть посилання, щоб побачити всі попередньо визначені формати та наявні шаблони формату; підручник доступний тут ). Цей новий API натхненний JodaTime .
String string = "January 2, 2010";
DateTimeFormatter formatter = DateTimeFormatter.ofPattern("MMMM d, yyyy", Locale.ENGLISH);
LocalDate date = LocalDate.parse(string, formatter);
System.out.println(date); // 2010-01-02
Примітка: якщо ваша форма формату також містить частину часу, тоді використовуйте LocalDateTime#parse(text, formatter)
замість LocalDate#parse(text, formatter)
. І якщо ваша формаформа також містить часовий пояс, тоді використовуйте ZonedDateTime#parse(text, formatter)
замість цього.
Ось витяг релевантності з javadoc з переліком усіх доступних моделей формату:
Symbol Meaning Presentation Examples
------ -------------------------- ------------ ----------------------------------------------
G era text AD; Anno Domini; A
u year year 2004; 04
y year-of-era year 2004; 04
D day-of-year number 189
M/L month-of-year number/text 7; 07; Jul; July; J
d day-of-month number 10
Q/q quarter-of-year number/text 3; 03; Q3; 3rd quarter
Y week-based-year year 1996; 96
w week-of-week-based-year number 27
W week-of-month number 4
E day-of-week text Tue; Tuesday; T
e/c localized day-of-week number/text 2; 02; Tue; Tuesday; T
F week-of-month number 3
a am-pm-of-day text PM
h clock-hour-of-am-pm (1-12) number 12
K hour-of-am-pm (0-11) number 0
k clock-hour-of-am-pm (1-24) number 0
H hour-of-day (0-23) number 0
m minute-of-hour number 30
s second-of-minute number 55
S fraction-of-second fraction 978
A milli-of-day number 1234
n nano-of-second number 987654321
N nano-of-day number 1234000000
V time-zone ID zone-id America/Los_Angeles; Z; -08:30
z time-zone name zone-name Pacific Standard Time; PST
O localized zone-offset offset-O GMT+8; GMT+08:00; UTC-08:00;
X zone-offset 'Z' for zero offset-X Z; -08; -0830; -08:30; -083015; -08:30:15;
x zone-offset offset-x +0000; -08; -0830; -08:30; -083015; -08:30:15;
Z zone-offset offset-Z +0000; -0800; -08:00;
Зверніть увагу, що в ньому є кілька заздалегідь визначених форматів для більш популярних моделей. Тому замість, наприклад DateTimeFormatter.ofPattern("EEE, d MMM yyyy HH:mm:ss Z", Locale.ENGLISH);
, ви можете використовувати DateTimeFormatter.RFC_1123_DATE_TIME
. Це можливо, тому що вони, навпаки SimpleDateFormat
, є безпечними для потоків. Таким чином, ви можете також визначити своє, якщо це необхідно.
Для конкретного формату рядка введення вам не потрібно використовувати явне DateTimeFormatter
: стандартну дату ISO 8601 , як-от 2016-09-26T17: 44: 57Z, можна проаналізувати безпосередньо, LocalDateTime#parse(text)
оскільки в ній вже використовується ISO_LOCAL_DATE_TIME
форматер. Аналогічно LocalDate#parse(text)
аналізує дату ISO без компонента часу (див. ISO_LOCAL_DATE
) Та ZonedDateTime#parse(text)
аналізує дату ISO з додаванням зміщення та часового поясу (див. ISO_ZONED_DATE_TIME
).