Analizowałem a java.util.Date
z, String
ale ustawia lokalną strefę czasową jako strefę czasową date
obiektu.
Strefa czasowa nie jest określona w, String
z którego Date
jest analizowany. Chcę ustawić określoną strefę czasową date
obiektu.
Jak mogę to zrobić?
java
date
timezone
java.util.date
Yatendra Goel
źródło
źródło
Odpowiedzi:
Użyj DateFormat. Na przykład,
źródło
TimeZone.setDefault()
przed wywołaniem,getTime()
aby nowy obiekt daty znalazł się w żądanej strefie czasowej. W JDK 1.8Calendar.getTime()
połączeniareturn new Date(getTimeInMillis());
.Należy pamiętać, że
java.util.Date
obiekty same w sobie nie zawierają żadnych informacji o strefie czasowej - nie można ustawić strefy czasowej naDate
obiekcie. Jedyne, coDate
zawiera obiekt, to kilka milisekund od „epoki” - 1 stycznia 1970 r., 00:00:00 UTC.Jak pokazuje ZZ Coder, ustawiasz strefę czasową na
DateFormat
obiekcie, aby powiedzieć mu, w której strefie czasowej chcesz wyświetlić datę i godzinę.źródło
long
zwane polefastTime
.Date.toString()
faktycznie używa aCalendar
do interpretacji tego milisekundowego czasu. Więc wypisanieDate
sprawia, że wydają się mieć (domyślne) strefę czasową, co prowadzi do zrozumiałych pytania dotyczące tego, jak ustawić strefę czasową.tl; dr
Brak strefy czasowej w czerwcu
Jak podają inne poprawne odpowiedzi, java.util.Date nie ma strefy czasowej † . Reprezentuje UTC / GMT (bez przesunięcia strefy czasowej). Bardzo mylące, ponieważ jego
toString
metoda stosuje domyślną strefę czasową maszyny JVM podczas generowania reprezentacji typu String.Unikaj juDate
Z tego i wielu innych powodów należy unikać korzystania z wbudowanego java.util.Date & .Calendar & java.text.SimpleDateFormat. Są notorycznie kłopotliwe.
Zamiast tego użyj pakietu java.time dołączonego do Java 8 .
java.time
Klasy java.time mogą reprezentować moment na osi czasu na trzy sposoby:
Instant
)OffsetDateTime
zZoneOffset
)ZonedDateTime
zZoneId
)Instant
W java.time podstawowym elementem konstrukcyjnym jest
Instant
chwila na linii czasu w UTC. UżywajInstant
obiektów przez większą część logiki biznesowej.OffsetDateTime
Zastosuj przesunięcie względem UTC aby dostosować się do czasu zegara ściennego w danej miejscowości .
Złóż
ZoneOffset
wniosek, aby uzyskaćOffsetDateTime
.ZonedDateTime
Lepiej jest zastosować strefę czasową , przesunięcie oraz zasady postępowania z anomaliami, takimi jak czas letni (DST) .
Zastosuj
ZoneId
do,Instant
aby uzyskaćZonedDateTime
. Zawsze określ prawidłową nazwę strefy czasowej . Nigdy nie używaj 3-4 skrótów, takich jakEST
lubIST
, które nie są ani unikalne, ani standardowe.LocalDateTime
Jeśli w łańcuchu wejściowym brakowało jakiegokolwiek wskaźnika przesunięcia lub strefy, parsuj jako
LocalDateTime
.Jeśli jesteś pewien planowanej strefy czasowej, przypisz a,
ZoneId
aby utworzyćZonedDateTime
. Zobacz przykładowy kod powyżej w sekcji tl; dr u góry.Sformatowane ciągi
Wywołaj
toString
metodę dowolnej z tych trzech klas, aby wygenerować ciąg znaków reprezentujący wartość daty i godziny w standardowym formacie ISO 8601 .ZonedDateTime
Klasa rozszerza standardowego formatu, dołączając nazwę strefy czasowej w nawiasie.W przypadku innych formatów użyj
DateTimeFormatter
klasy. Ogólnie najlepiej, aby pozwolić tej klasie generować zlokalizowane formaty przy użyciu oczekiwanego języka ludzkiego i norm kulturowych. Lub możesz określić konkretny format.O java.time
Środowisko java.time jest wbudowane w Javę 8 i nowsze wersje . Klasy te kłopotliwe zastąpić stary starszych klas Date-Time, takich jak
java.util.Date
,Calendar
, iSimpleDateFormat
.Projekt Joda-Time , teraz w trybie konserwacji , zaleca migrację do klas java.time .
Aby dowiedzieć się więcej, zobacz samouczek Oracle . I przeszukaj stos przepełnienia dla wielu przykładów i wyjaśnień. Specyfikacja to JSR 310 .
Możesz wymieniać obiekty java.time bezpośrednio ze swoją bazą danych. Użyj sterownika JDBC zgodnego z JDBC 4.2 lub nowszym. Nie potrzeba ciągów, nie ma potrzeby
java.sql.*
klas.Gdzie można uzyskać klasy java.time?
Projekt ThreeTen-Extra rozszerza java.time o dodatkowe klasy. Ten projekt jest poligonem doświadczalnym dla ewentualnych przyszłych dodatków do java.time. Można znaleźć kilka przydatnych klas tutaj takie jak
Interval
,YearWeek
,YearQuarter
, i więcej .Joda-Time
Chociaż Joda-Time jest nadal aktywnie utrzymywany, jego twórcy powiedzieli nam, abyśmy migrowali do java.time, gdy tylko będzie to wygodne. Zostawiam tę sekcję nietkniętą jako odniesienie, ale sugeruję użycie
java.time
zamiast tego powyższej sekcji.W Joda-Time obiekt date-time (
DateTime
) naprawdę zna swoją przypisaną strefę czasową. Oznacza to przesunięcie w stosunku do UTC oraz zasad i historii czasu letniego (DST) w tej strefie czasowej i innych tego rodzaju anomalii.Wywołaj
toString
metodę, aby wygenerować ciąg znaków w formacie ISO 8601 .Joda-Time oferuje również bogate możliwości generowania wszelkiego rodzaju innych formatów String.
W razie potrzeby możesz przekonwertować z Joda-Time DateTime na java.util.Date.
Wyszukaj StackOverflow dla „joda date”, aby znaleźć wiele innych przykładów, niektóre dość szczegółowe.
† To właśnie tam znajduje się strefa czas osadzony w java.util.Date, używane do niektórych funkcji wewnętrznych (patrz komentarze na tę odpowiedź). Ale ta wewnętrzna strefa czasowa nie jest ujawniana jako właściwość i nie można jej ustawić. Ta wewnętrzna strefa czasowa nie jest używana przez
toString
metodę do generowania ciągu reprezentującego wartość daty i godziny; zamiast tego bieżąca domyślna strefa czasowa JVM jest stosowana w locie. Tak więc, jak stenografia, często mówimy „juDate nie ma strefy czasowej”. Mylące? Tak. To kolejny powód, aby unikać tych zmęczonych starych klas.źródło
BaseCalendar.Date cdate
właściwości, jeśli jest ustawiona. Spójrz na kod źródłowy tutaj . Nie możesz ustawić strefy czasowej obiektu juDate, chyba że zmienisz domyślną strefę czasową JVM przez wywołanieTimeZone.setDefault(TimeZone.getTimeZone("NEW_TIME_ZONE"));
. Zatem istnieje przesunięcie strefy czasowej i można je uzyskać, wywołując przestarzałą metodę juDate.getTimezoneOffset ()toString
metody, która stosuje bieżącą domyślną strefę czasową JVM; ponownie ignorując zakopaną strefę czasową. Dla zwięzłości mówimy, że java.util.Date nie ma strefy czasowej. Podobnie jak sztuka , to kłamstwo mówi prawdę.TimeZone.setDefault
, nie ustawiasz strefy czasowej obiektu java.util.Date - obiekt Date nadal ignoruje swoją ukrytą strefę czasową, działając skutecznie w UTC. Wpłynąłbyś natoString
metodę Date . Ustawienie wartości domyślnej zmienia domyślną strefę czasową maszyny JVM, która jest zwykle ustawiona na strefę czasową systemu operacyjnego hosta. To wywołanie nie jest zalecane, ponieważ wpływa na cały kod we wszystkich wątkach wszystkich aplikacji działających w tej JVM i robi to w locie podczas ich wykonywania. Będąc niegrzecznym i niebezpiecznym, to połączenie powinno być traktowane tylko jako ostateczność.equals
,hashcode
,getTime
..) Jeśli spojrzeć naequals
metodzie, wywołujegetTime()
który wzywagetTimeImpl()
, który wzywanormalize()
, jeżelicdate
nieruchomość nie jest znormalizowane. Wnormalize()
metodzie ostatni warunek if ponownie oblicza milisekundy od 1/1/70 na podstawie przechowywanych informacji o strefie czasowej, jeśli strefa czasowacdate
jest inna niż strefa czasowa bieżącego środowiska JVM, na którym działa. (Spójrz nasun.util.calendar.AbstractCalendar getCalendarDate(long millis, CalendarDate date)
)Możesz także ustawić strefę czasową na poziomie JVM
wynik:
źródło
TimeZone.setDefault
jest dość drastyczne, ponieważ wpływa na całą JVM, wpływa na wszystkie inne obiekty i wątki. Zobacz tę odpowiedź, aby uzyskać szczegółowe informacje, w tym jeszcze więcej komplikacji, jeśli korzystasz z SecurityManager. Dodanie jeszcze większej komplikacji: zachowanie to zmieniło się w różnych wersjach Java, jak omówiono w tym pytaniu .Jeśli musisz pracować tylko ze standardowymi klasami JDK, możesz użyć tego:
Kredyt trafia do tego postu .
źródło
java.util.Calendar
jest zwykłym sposobem obsługi stref czasowych przy użyciu tylko klas JDK. Apache Commons ma kilka innych alternatyw / narzędzi, które mogą być pomocne. Edytuj notatkę Sponga przypomniało mi, że słyszałem naprawdę dobre rzeczy o Joda-Time (chociaż sam tego nie używałem).źródło
Period
,Duration
iInterval
. Przęsła te obejmują metody, takie jak porównaniecontains
,abuts
,overlap
igap
. IPeriodFormatterBuilder
może budować opisowe frazy, takie jak „15 lat i 8 miesięcy”.Konwertuj datę na ciąg i zrób to za pomocą SimpleDateFormat.
źródło
Jeśli ktoś tego kiedykolwiek potrzebuje, jeśli chcesz przekonwertować
XMLGregorianCalendar
strefę czasową na aktualną strefę czasową z UTC, wystarczy ustawić strefę czasową na0
, a następnie zadzwonićtoGregorianCalendar()
- pozostanie ta sama strefa czasowa, aleDate
wie, jak ją przekonwertować twoje, abyś mógł uzyskać stamtąd dane.Wynik:
źródło
Ten kod był pomocny w aplikacji, nad którą pracuję:
źródło