vergleichen - Java-Datum im Vergleich zum Kalender




java gregorian calendar (8)

Könnte jemand bitte die aktuelle "Best Practice" um Date und Calendar raten.

Wenn Sie neuen Code schreiben, ist es am besten, Calendar über Date immer zu bevorzugen, oder gibt es Umstände, in denen Date der geeignetere Datentyp ist?


tl; dr

Beraten Sie die aktuelle "Best Practice" um Date und Calendar

ist es am besten, Calendar über Date immer zu bevorzugen

Vermeiden Sie diese Legacy-Klassen vollständig. Verwenden java.time stattdessen java.time Klassen.

Einzelheiten

Die Antwort von Ortomala Lokni ist richtig zu empfehlen, die modernen java.time Klassen anstelle der lästigen alten Legacy-Date-Time-Klassen ( Date , Calendar , etc.) zu verwenden. Aber diese Antwort schlägt die falsche Klasse als gleichwertig vor (siehe meinen Kommentar zu dieser Antwort).

Verwenden von java.time

Die java.time-Klassen sind eine enorme Verbesserung gegenüber den bisherigen Datum-Zeit-Klassen und dem Unterschied zwischen Tag und Nacht. Die alten Klassen sind schlecht gestaltet, verwirrend und mühsam. Sie sollten die alten Klassen möglichst vermeiden. Wenn Sie jedoch zu / von alt / neu konvertieren müssen, können Sie dies tun, indem Sie neue Methoden zu den alten Klassen hinzufügen.

Weitere Informationen zur Konvertierung finden Sie unter Antwort und geschicktes Diagramm auf eine andere Frage. Konvertieren Sie java.util.Date in den Typ "java.time". .

Die Suche nach bietet viele hundert Beispiele für Fragen und Antworten zur Verwendung von java.time. Aber hier ist eine kurze Zusammenfassung.

Instant

Holen Sie sich den aktuellen Moment mit einem Instant . Die Instant Klasse repräsentiert einen Moment auf der Timeline in UTC mit einer Auflösung von nanoseconds (bis zu neun (9) Ziffern eines Dezimalbruchteils).

Instant instant = Instant.now();

ZonedDateTime

Um den gleichen simultanen Moment durch die Linse der ZoneId einer bestimmten Region zu sehen , wenden Sie eine Zeitzone ( ZoneId ) an, um eine ZonedDateTime .

Zeitzone

Geben Sie einen korrekten Zeitzonennamen im Format continent/region , z. B. America/Montreal , Africa/Casablanca oder Pacific/Auckland . Verwenden Sie niemals die 3-4-Buchstaben-Abkürzung wie EST oder IST da sie keine echten Zeitzonen sind, nicht standardisiert und nicht einmal eindeutig (!).

ZoneId z = ZoneId.of( "America/Montreal" );
ZonedDateTime zdt = instant.atZone();

Offset

Eine Zeitzone ist eine Geschichte von Änderungen der offset-from-UTC Zeit in einer Region. Aber manchmal bekommt man nur einen Offset ohne die volle Zone. Verwenden OffsetDateTime in diesem Fall die OffsetDateTime Klasse.

ZoneOffset offset = ZoneOffset.parse( "+05:30" );
OffsetDateTime odt = instant.atOffset( offset );

Die Verwendung einer Zeitzone ist gegenüber der Verwendung eines bloßen Versatzes vorzuziehen.

LocalDateTime

Das "Lokale" in den Local… Klassen bedeutet jeden Ort, nicht einen bestimmten Ort. So kann der Name kontraintuitiv sein.

LocalDateTime , LocalDate und LocalTime fehlen absichtlich keine Informationen über Offset oder Zeitzone. Sie repräsentieren also keine tatsächlichen Momente, sie sind keine Punkte auf der Timeline. Verwenden ZonedDateTime im Zweifelsfall oder bei Unklarheiten " ZonedDateTime anstelle von " LocalDateTime . Durchsuchen Sie für viel mehr Diskussion.

Saiten

Verknüpfen Sie Datums- und Uhrzeitobjekte nicht mit Zeichenfolgen, die ihren Wert darstellen. Sie können eine Zeichenfolge analysieren, um ein Datum-Uhrzeit-Objekt abzurufen, und Sie können eine Zeichenfolge aus einem Datum-Uhrzeit-Objekt generieren. Aber die Zeichenfolge ist niemals das Datum-Uhrzeit selbst.

Informieren Sie sich über standardmäßige ISO 8601- Formate, die standardmäßig in den java.time-Klassen verwendet werden.

Über java.time

Das Framework java.time ist in Java 8 und höher integriert. Diese Klassen ersetzen die problematischen alten legacy Date-Time-Klassen wie java.util.Date , Calendar und SimpleDateFormat .

Das Joda-Time Projekt, das sich jetzt im Wartungsmodus befindet , empfiehlt die Migration in die java.time Klassen.

Weitere Informationen finden Sie im Oracle-Lernprogramm . Und suchen Sie nach für viele Beispiele und Erklärungen. Spezifikation ist JSR-310 .

Mit einem JDBC-Treiber, der JDBC 4.2 oder höher entspricht, können Sie java.time- Objekte direkt mit Ihrer Datenbank austauschen. Keine Notwendigkeit für Strings noch java.sql. * Klassen.

Wo erhalten Sie die java.time Klassen?

  • Java SE 8 , Java SE 9 und höher
    • Eingebaut.
    • Teil der Standard-Java-API mit einer gebündelten Implementierung.
    • Java 9 fügt einige kleinere Funktionen und Korrekturen hinzu.
  • Java SE 6 und Java SE 7
  • Android
    • Spätere Versionen von Android-Bundle-Implementierungen der java.time-Klassen.
    • Für ältere Android- ThreeTenABP passt das ThreeTenABP Projekt den ThreeTen-Backport ( siehe oben) an. Siehe Verwendung von ThreeTenABP ....

Das ThreeTen-Extra Projekt erweitert java.time um zusätzliche Klassen. Dieses Projekt ist ein Testfeld für mögliche zukünftige Erweiterungen von java.time. Sie können hier einige nützliche Klassen wie Interval , YearWeek , YearQuarter und more .


Btw "date" wird in der Regel als "obsolet / deprecated" markiert (ich weiß nicht genau warum) - etwas darüber ist dort geschrieben Java: Warum ist der Date-Konstruktor veraltet, und was verwende ich stattdessen?

Es sieht so aus, als wäre es nur ein Problem des Konstruktors über neues Date (int year, int month, int day) , empfohlener Weg ist über Calendar und set params separat. ( Calendar cal = Calendar.getInstance (); )


Datum ist eine einfachere Klasse und ist hauptsächlich aus Gründen der Rückwärtskompatibilität vorhanden. Verwenden Sie einen Kalender, wenn Sie bestimmte Daten festlegen oder Datumsarithmetik ausführen müssen. Kalender übernehmen auch die Lokalisierung. Die früheren Datumsmanipulationsfunktionen von Date sind seither veraltet.

Persönlich tendiere ich dazu, entweder die Zeit in Millisekunden als lang (oder Long, wie passend) oder den Kalender zu verwenden, wenn es eine Wahlmöglichkeit gibt.

Sowohl das Datum als auch der Kalender sind änderbar, was zu Problemen bei der Verwendung in einer API führt.


Datum sollte neu entwickelt werden. Anstatt ein langer Interger zu sein, sollte er Jahr, Monat, Datum, Stunde, Minute, Sekunde als separate Felder enthalten. Es kann sogar sinnvoll sein, den Kalender und die Zeitzone zu speichern, mit denen dieses Datum verknüpft ist.

In unserer natürlichen Konversation, wenn Sie einen Termin am 1. November 2013 1pm NY Zeit einrichten, ist dies eine DateTime. Es ist kein Kalender. Wir sollten uns also auch auf Java unterhalten können.

Wenn Datum als lange Ganzzahl gespeichert wird (in Millisekunden seit dem 1. Januar 1970 oder so), hängt die Berechnung des aktuellen Datums vom Kalender ab. Verschiedene Kalender geben ein anderes Datum an. Dies ist aus der Perspektive, eine absolute Zeit zu geben (zB 1 Billion Sekunden nach dem Urknall). Oft brauchen wir aber auch eine bequeme Art der Konversation, etwa ein Objekt, das Jahr, Monat etc. kapselt.

Ich frage mich, ob es in Java neue Fortschritte gibt, um diese beiden Ziele zu erreichen. Vielleicht ist mein Java-Wissen zu alt.


Ein bisschen spät auf der Party, aber Java hat eine neue Date Time API in JDK 8. Vielleicht möchten Sie Ihre JDK-Version aktualisieren und den Standard übernehmen. Kein unordentliches Datum / Kalender mehr, keine 3rd Party Gläser mehr.


Ich befürworte immer joda-time.sourceforge.net . Hier ist der Grund.

  1. Die API ist konsistent und intuitiv. Im Gegensatz zu den java.util.Date/Calendar APIs
  2. Im Gegensatz zu java.text.SimpleDateFormat usw. gibt es keine Threading-Probleme. (Ich habe zahlreiche java.text.SimpleDateFormat gesehen, die darauf zurückzuführen sind, dass die Standardformatierung von Datum und Uhrzeit nicht threadsicher ist).
  3. Es ist die Grundlage der neuen Java-APIs für Datum und Uhrzeit ( JSR310 , geplant für Java 8. Sie verwenden also APIs, die zu zentralen Java-APIs werden.

Mit Java 8 sollte das neue Paket java.time verwendet werden.

Objekte sind unveränderbar, Zeitzonen und Tageslichteinsparung werden berücksichtigt.

Sie können ein ZonedDateTime Objekt aus einem alten java.util.Date Objekt wie ZonedDateTime erstellen:

    Date date = new Date();
    ZonedDateTime zonedDateTime = date.toInstant().atZone(ZoneId.systemDefault());

Date s sollte als unveränderbare Zeitpunkte verwendet werden; Calendar sind änderbar und können weitergegeben und geändert werden, wenn Sie mit anderen Klassen zusammenarbeiten müssen, um ein endgültiges Datum zu erhalten. Betrachten Sie sie analog zu String und StringBuilder und Sie werden verstehen, wie ich denke, dass sie verwendet werden sollten.

(Und ja, ich weiß, Datum ist eigentlich nicht technisch unveränderlich, aber die Absicht ist, dass es nicht änderbar sein sollte, und wenn nichts die veralteten Methoden nennt, dann ist es so.)





calendar