Java setTimeZone изменение даты - PullRequest
0 голосов
/ 23 октября 2019

Я анализирую строку "15.11.2020" в дату. Мне нужно установить часовой пояс на EDT, но это меняет дату на 14.11.2020. Я предполагаю, потому что я нахожусь в CST, он удаляет эту разницу времени в часах с: Sun Nov 15 00:00:00 CST 2020, и это становится предыдущим днем.

Я бы хотел установить часовой пояс без изменения даты. Как я могу сделать это? Недостаточно просто добавить час.

dateFormat dataFormat = new SimpleDateFormat("MM/dd/yy");
dataFormat.setTimeZone(TimeZone.getTimeZone(Constants.EDT_TZN));

Ответы [ 2 ]

2 голосов
/ 23 октября 2019

Дата не имеет часового пояса.

. Я бы хотел установить часовой пояс без изменения даты.

Значение только для даты, например 15 ноября 2020 года, не имеет понятия о часовом поясе. Вам не нужно беспокоиться о часовых поясах.

Избегайте устаревших классов даты и времени

Вы используете ужасные классы даты и времени, которые были вытеснены несколько лет назад java.time классов, определенных в JSR 310. Никогда не используйте SimpleDateFormat, Date или Calendar.

Table of date-time types in Java (both legacy and modern) and in standard SQL.

LocalDate

В Java значение только для даты без времени суток и без времени суток представлено классом LocalDate.

String input = "11/15/2020" ;
DateTimeFormatter f = DateTimeFormatter.ofPattern( "MM/dd/uuuu" ) ;
LocalDate ld = LocalDate.parse( input , f ) ;

См. Этот код, запущенный вживуюat IdeOne.com .

ld.toString: 2020-11-15

Момент

Возможно, вам нужен момент, а непросто свиданиеЯ предполагаю, что это будет означать, что вы хотите первый момент дня.

Не думайте, что день начинается в 00:00:00. Аномалии, такие как переход на летнее время (DST), означают, что день может начинаться в такое время, как 01:00:00. Пусть java.time определяет, с чего начинается определенный день в определенном часовом поясе.

Укажите правильное имя часового пояса в формате Continent/Region, напримерAmerica/Montreal, Africa/Casablanca или Pacific/Auckland. Никогда не используйте 2-4 буквенные сокращения, такие как EST, EDT, CST или IST, поскольку они не истинные часовые пояса, не стандартизированы и даже не уникальны (!),Например, CST может быть китайским стандартным временем так же легко, как центральное стандартное время в Северной и Южной Америке.

ZoneId z = ZoneId.of( "America/Montreal" ) ;
ZonedDateTime zdt = ld.atStartOfDay( z ) ;

zdt.toString (): 2020-11-15T00: 00-05:00 [Америка / Монреаль]

Обычно лучше всего хранить и обмениваться моментами в UTC. Чтобы перейти из указанного часового пояса в UTC, извлеките Instant из ZonedDateTime. Instant всегда по UTC по определению.

Instant instant = zdt.toInstant() ;

instant.toString (): 2020-11-15T05: 00: 00Z

Создать текст встандартный ISO 8601 формат. Z в конце означает UTC и произносится как «зулу».

instant.toString (): 2020-11-15T05: 00: 00Z

Преобразование

Если необходимо взаимодействовать со старым кодом, который еще не обновленв java.time вы можете конвертировать туда и обратно. Посмотрите на новые to… / from… методы, добавленные к старым классам.

Устаревший класс Date, хотя и ошибочно назван, эквивалентен Instant, оба представляют момент в UTC. Instant использует более высокое разрешение, чем наносекунды, а не миллисекунды.

Date d = java.util.Date.from( instant ) ;

… и…

Instant instant = d.toInstant() ;

Помните, что метод Date::toString говорит ложь , применяя текущий часовой пояс по умолчанию. Несмотря на благие намерения, на практике это довольно запутанно. Одна из многих причин, чтобы избежать этого класса.

1 голос
/ 23 октября 2019

Время в Java (согласно объекту Date и System.currentTimeMillis) определяется как миллисекунды после 1 января 1970 года, 00:00:00 по Гринвичу. Все настройки TimeZone - это локализация смещения в часах в определенное (Java) время.

Таким образом, у вас есть три варианта:

  1. Не добавляйте дополнительный час и не устанавливайтечасовой пояс EST, в этом случае вы получите новую дату.
  2. Добавьте дополнительный час, в этом случае дата останется прежней
  3. Найдите или создайте свой собственный пакет времени / даты
...