Kenapa
ZonedDateTime now = ZonedDateTime.now();
System.out.println(now.withZoneSameInstant(ZoneOffset.UTC)
.equals(now.withZoneSameInstant(ZoneId.of("UTC"))));
mencetak false?
Saya berharap kedua ZonedDateTimecontoh sama.
Kenapa
ZonedDateTime now = ZonedDateTime.now();
System.out.println(now.withZoneSameInstant(ZoneOffset.UTC)
.equals(now.withZoneSameInstant(ZoneId.of("UTC"))));
mencetak false?
Saya berharap kedua ZonedDateTimecontoh sama.
Jawaban:
Jawabannya berasal dari javadocZoneId (penekanan saya) ...
ZoneId digunakan untuk mengidentifikasi aturan yang digunakan untuk mengonversi antara Instan dan LocalDateTime. Ada dua jenis ID yang berbeda:
- Offset tetap - offset yang diselesaikan sepenuhnya dari UTC / Greenwich, yang menggunakan offset yang sama untuk semua tanggal-waktu lokal
- Kawasan geografis - area di mana sekumpulan aturan khusus untuk menemukan pengimbangan dari UTC / Greenwich berlaku
Sebagian besar offset tetap diwakili oleh ZoneOffset. Memanggil normalized () pada ZoneId mana pun akan memastikan bahwa ID offset tetap akan direpresentasikan sebagai ZoneOffset.
... dan dari javadocZoneId#of (penekanan saya):
Metode ini mem-parsing ID yang menghasilkan ZoneId atau ZoneOffset. ZoneOffset dikembalikan jika ID-nya adalah 'Z', atau dimulai dengan '+' atau '-' .
Id argumen ditentukan sebagai "UTC", oleh karena itu ia akan mengembalikan ZoneIddengan offset, yang juga disajikan dalam bentuk string:
System.out.println(now.withZoneSameInstant(ZoneOffset.UTC));
System.out.println(now.withZoneSameInstant(ZoneId.of("UTC")));
Keluaran:
2017-03-10T08:06:28.045Z
2017-03-10T08:06:28.045Z[UTC]
Saat Anda menggunakan equalsmetode untuk perbandingan, Anda memeriksa kesetaraan objek . Karena perbedaan yang dijelaskan, hasil evaluasi adalah false.
Ketika normalized()metode digunakan seperti yang diusulkan dalam dokumentasi, perbandingan menggunakan equalsakan kembali true, seperti yang normalized()akan mengembalikan ZoneOffset:
Menormalkan ID zona waktu, mengembalikan ZoneOffset jika memungkinkan.
now.withZoneSameInstant(ZoneOffset.UTC)
.equals(now.withZoneSameInstant(ZoneId.of("UTC").normalized())); // true
Seperti yang dinyatakan dalam dokumentasi, jika Anda menggunakan "Z"atau "+0"sebagai input id, ofakan mengembalikan ZoneOffsetsecara langsung dan tidak perlu memanggil normalized():
now.withZoneSameInstant(ZoneOffset.UTC).equals(now.withZoneSameInstant(ZoneId.of("Z"))); //true
now.withZoneSameInstant(ZoneOffset.UTC).equals(now.withZoneSameInstant(ZoneId.of("+0"))); //true
Untuk memeriksa apakah mereka menyimpan waktu tanggal yang sama , Anda dapat menggunakan isEqualmetode ini sebagai gantinya:
now.withZoneSameInstant(ZoneOffset.UTC)
.isEqual(now.withZoneSameInstant(ZoneId.of("UTC"))); // true
Sampel
System.out.println("equals - ZoneId.of(\"UTC\"): " + nowZoneOffset
.equals(now.withZoneSameInstant(ZoneId.of("UTC"))));
System.out.println("equals - ZoneId.of(\"UTC\").normalized(): " + nowZoneOffset
.equals(now.withZoneSameInstant(ZoneId.of("UTC").normalized())));
System.out.println("equals - ZoneId.of(\"Z\"): " + nowZoneOffset
.equals(now.withZoneSameInstant(ZoneId.of("Z"))));
System.out.println("equals - ZoneId.of(\"+0\"): " + nowZoneOffset
.equals(now.withZoneSameInstant(ZoneId.of("+0"))));
System.out.println("isEqual - ZoneId.of(\"UTC\"): "+ nowZoneOffset
.isEqual(now.withZoneSameInstant(ZoneId.of("UTC"))));
Keluaran:
equals - ZoneId.of("UTC"): false
equals - ZoneId.of("UTC").normalized(): true
equals - ZoneId.of("Z"): true
equals - ZoneId.of("+0"): true
isEqual - ZoneId.of("UTC"): true
ZoneId.of("Z")memberi AndaZoneOffset.UTCtetapiZoneId.of("UTC")memberi AndaZoneId(yang tidakZoneOffset.UTC). API ini tidak intuitif, untuk sedikitnya.