LoginSignup
10
15

More than 5 years have passed since last update.

SimpleDateFormatとDateTimeFormatterの違いってなんだ??

Last updated at Posted at 2018-05-14

SimpleDateFormatとDateTimeFormatterの違いってなんだ??

自分がこの前書いた記事で、SimpleDateFormatとDateTimeFormatterを使用した。
どちらも日付時刻フォーマッターで、一体何が違うのか把握できていなかったので、調べてみた。

インスタンス生成の違い

newするか、用意されているメソッドを使用するかの違いがある。

SimpleDateFormatの場合

SimpleDateFormatのインスタンス生成は、newして生成する。
スレッドセーフではない。
そのため、マルチスレッド処理の場合、使用する直前で毎回インスタンスを生成することが必要。

SimpleDateFormat sdf = new SimpleDateFormat("yyyy/MM/dd HH:mm:ss.SSS");

DateTimeFormatterの場合

DateTimeFormatterのインスタンス生成は、ofPatternメソッドで生成する。
スレッドセーフ。
SimpleDateFormatと違って、マルチスレッド処理のとき、使うたびにインスタンスを生成するということが必要ない。

DateTimeFormatter dtf = DateTimeFormatter.ofPattern("yyyy/MM/dd HH:mm:ss.SSS");

parse(解析)

StringをSimpleDateFormatとDateTimeFormatterを使って変換してみる。

SimpleDateFormatの場合

String → Dateに変換する処理。
parseメソッドにString型を引数として渡すのみ。
ParseExceptionの例外処理が必要だけど、下の例では省略。

SimpleDateFormat sdf = new SimpleDateFormat("yyyy/MM/dd HH:mm:ss.SSS");
Date date = sdf.parse("2018/05/14 12:34:56.123");
// Mon May 14 12:34:56 UTC 2018
System.out.println(date);

DateTimeFormatterの場合

String → TemporalAccessorに変換する処理。

DateTimeFormatter dtf = DateTimeFormatter.ofPattern("yyyy/MM/dd HH:mm:ss.SSS");
TemporalAccessor ta = dtf.parse("2018/05/14 12:34:56.123");
// {},ISO resolved to 2018-05-14T12:34:56.123
System.out.println(ta);

TemporalAccessorってなに…?ってなった。出力結果も"ISO resolved to ~~"とかついている。
LocalDateTimeの親インターフェースらしい。他にもLocalDate, LocalTime, ZonedDateTimeの親にあたる。
なので、こんなことが可能。
※ 自分で書いておいて「だからなに…?」ってなっていますが、備忘録として記載。

TemporalAccessor tAccessor = LocalDateTime.of(2018, 5, 14, 12, 34, 56);

DateTimeFommaterでparseする場合、LocalDateTimeのparseメソッドが使用されているパターンが多いと思われる。
下のようになる。こちらのほうが使用頻度高そうなので覚えておきたい。
(String → LocalDateTimeに変換する処理。)

DateTimeFormatter dtf = DateTimeFormatter.ofPattern("yyyy/MM/dd HH:mm:ss.SSS");
LocalDateTime date = LocalDateTime.parse("2018/05/14 12:34:56.123", dtf);
// 2018-05-14T12:34:56.123
System.out.println(date);

format(整形)

SimpleDateFormatとDateTimeFormatterをその名の通りフォーマットしてみる。

SimpleDateFormatの場合

Date→Stringに変換する処理。
formatメソッドにjava.util.Date型を引数として渡す。

SimpleDateFormat sdf = new SimpleDateFormat("yyyy/MM/dd HH:mm:ss.SSS");
Date date = sdf.parse("2018/05/14 12:34:56.123");
// Mon May 14 12:34:56 UTC 2018
System.out.println(date);

String str = sdf.format(date);
// 2018/05/14 12:34:56.123
System.out.println(str);

DateTimeFormatterの場合

formatメソッドにTemporalAccessorを引数として渡す。

DateTimeFormatter dtf = DateTimeFormatter.ofPattern("yyyy/MM/dd HH:mm:ss.SSS");
LocalDateTime date = LocalDateTime.parse("2018/05/14 12:34:56.123", dtf);
// 2018-05-14T12:34:56.123
System.out.println(date);

String str = dtf.format(date);
// 2018/05/14 12:34:56.123
System.out.println(str);

まとめ

だらだらと書いてしまったが、わかったことをまとめると、

SimpleDateFormat DateTimeFormatter
java.util.Dateへの変換 TemporalAccessorへの変換(LocalDateTime, LocalDate, LocalTime, ZonedDateTimeなど)
インスタンス生成 new SimpleDateFormat("yyyy/MM/dd HH:mm:ss.SSS") DateTimeFormatter.ofPattern("yyyy/MM/dd HH:mm:ss.SSS")
スレッドセーフ? ×
parse dtf.parse(str)
java.util.Dateになる。
dtf.parse(str)
TemporalAccessorになる。
LocalDateTimeなどのparseメソッドのほうが使いやすい。
format sdf.format(date) dtf.format(TemporalAccessor)

Javaの日付/時刻の扱いはやっぱり難しい。
PHPはこんなに難しくなったような気がする。
(日付/時刻を扱ったことがあまりないからそう思っているだけかも…)

10
15
2

Register as a new user and use Qiita more conveniently

  1. You get articles that match your needs
  2. You can efficiently read back useful information
  3. You can use dark theme
What you can do with signing up
10
15