Date/Calendar↔Date And Time API系変換のまとめ
Instantを介することで変換可能。その手順のまとめ。
Java | Java SE 8 |
Date/Calendar↔Date And Time API系の変換は、Instantを介して行う。それぞれのクラスでInstantを直接扱えるのかどうかなどが異なるため、手順をまとめる。
Date/Calendar→Date And Time API系の変換

Date/CalendarからDate And Time API系へ変換する場合は、まずXXXDateTimeへの変換を考える。「LocalDate」「LocalTime」「Year」「YearMonth」などはXXXDateTimeから変換メソッドが用意されているので、とりあえずXXXDateTimeにしてしまう。
Date/CalendarからXXXDateTimeへの変換はInstantを介して行う。Date/CalendarにはInstantを取得できるtoInstant()メソッドが、Java8から追加された。Instantはエポック時間からの経過秒が保持されている。ただしInstantだけでは表現したい時差やタイムゾーンが不明のため、XXXDateTimeにするには「ZoneId」or「ZoneOffset」が必要になる。システムデフォルトのZoneIdはZoneId.systemDefault()で取得できる。
Date→LocalDateTime
LocalDateTimeの場合、エポック秒から生成できるofEpochSecond()が用意されている。ただZoneIdからZoneOffsetを取得するのは手順が面倒なため、instantとzoneIdで生成できるofInstant()が用意されている。それを利用する。
Date date = new Date();
Instant instant = date.toInstant();
ZoneId zone = ZoneId.systemDefault();
LocalDateTime converted = LocalDateTime.ofInstant(instant, zone);
Date→OffsetDateTime
OffsetDateTimeの場合、「ZoneId」「ZoneOffset」のどちらからでも生成できる。ZoneIdはZoneOffsetの情報を取得できるので可能。
Date date = new Date();
Instant instant = date.toInstant();
ZoneOffset offset = ZoneOffset.ofHours(9);
OffsetDateTime converted = instant.atOffset(offset);
Date date = new Date();
Instant instant = date.toInstant();
ZoneId zone = ZoneId.systemDefault();
OffsetDateTime converted = OffsetDateTime.ofInstant(instant, zone);
Date→ZonedDateTime
ZonedDateTimeの場合、instantとzoneIdから生成できる。InstantクラスにもZonedDateTimeを生成できるファクトリがあるが、内部的に ZonedDateTime.ofInstant()呼び出すのでどちらでもいい。
Date date = new Date();
Instant instant = date.toInstant();
ZoneId zone = ZoneId.systemDefault();
ZonedDateTime converted = ZonedDateTime.ofInstant(instant, zone);
Calendar→LocalDateTime,OffsetDateTime,ZonedDateTime
CalendarもtoInstant()があるのでInstantを介した変換が可能。instant取得後は同様の手順。
Calendar calendar = Calendar.getInstance();
Instant instant = calendar.toInstant();
ZoneId zone = ZoneId.systemDefault();
LocalDateTime converted = LocalDateTime.ofInstant(instant, zone);
Date And Time API系→Date/Calendarの変換

Date And Time API系からDate/Calendarへ変換する場合は、まず「OffsetDateTime」「ZonedDateTime」への変換を考える。Instantを取得することでDate/Calendarへの変換が可能になる。ただし、InstantからCalendarを直接生成することができない。Dateを生成してからCalendarへ変換する手順になる。
Date/Calendarへの変換においては、LocalDateTimeが直接Instatntを作れない。LocalDateTimeが示している日時がどの時差あるいはタイムゾーンなのかの情報を持たないため、Instantは生成できないことになる。よって「LocalDate」「LocalTime」「Year」「YearMonth」などと同様に、「OffsetDateTime」「ZonedDateTime」を経由してInstantを生成する。
LocalDateTime→Date
LocalDateTimeからInstantは直接生成できないので、OffsetDateTime かZonedDateTimeを経由する。
LocalDateTime localDateTime = LocalDateTime.now();
ZoneId zone = ZoneId.systemDefault();
ZonedDateTime zonedDateTime = ZonedDateTime.of(localDateTime, zone);
Instant instant = zonedDateTime.toInstant();
Date date = Date.from(instant);
OffsetDateTime→Date
OffsetDateTimeはInstantを生成できるので、そのまま変換可能。
OffsetDateTime offsetDateTime = OffsetDateTime.now();
Instant instant = offsetDateTime.toInstant();
Date date = Date.from(instant);
ZonedDateTime→Date
ZonedDateTimeはInstantを生成できるので、そのまま変換可能。
ZonedDateTime zonedDateTime = ZonedDateTime.now();
Instant instant = zonedDateTime.toInstant();
Date date = Date.from(instant);
LocalDateTime,OffsetDateTime,ZonedDateTime→Calendar
CalendarはInstantを生成できるが、InstantからCalendarを生成できない。Dateを経由して、Date→Calendar変換を行う。「OffsetDateTime」「ZonedDateTime」も同様の手順。
LocalDateTime localDateTime = LocalDateTime.now();
ZoneId zone = ZoneId.systemDefault();
ZonedDateTime zonedDateTime = ZonedDateTime.of(localDateTime, zone);
Instant instant = zonedDateTime.toInstant();
Date date = Date.from(instant);
Calendar calendar = Calendar.getInstance();
calendar.setTime(date);
GregorianCalendar↔ZonedDateTimeの変換
Calendarの中でもGregorianCalendarのみ特殊で、ZonedDateTimeと相互変換が可能。
GregorianCalendarがグレゴリオ暦かつタイムゾーンを保持しているので、ZonedDateTimeととても近いため。ただしGregorianCalendarとZonedDateTimeはユリウス/グレゴリオ暦の切換え日のサポート有無が異なるため、そこだけ注意。
GregorianCalendar gregorianCalendar = new GregorianCalendar();
ZonedDateTime converted = gregorianCalendar.toZonedDateTime();
ZonedDateTime zonedDateTime = ZonedDateTime.now();
GregorianCalendar gregorianCalendar = GregorianCalendar.from(zonedDateTime);
Appendix A: 参考
Appendix B: 改訂履歴
-
v1.0, 2016-07-12: 初稿