Как извлечь эпоху из LocalDate и LocalDateTime?



как извлечь значение эпохи в Long экземпляров LocalDateTime или LocalDate? Я пробовал
следующие, но это дает мне другие результаты:



LocalDateTime time = LocalDateTime.parse("04.02.2014  19:51:01", DateTimeFormatter.ofPattern("dd.MM.yyyy  HH:mm:ss"));
System.out.println(time.getLong(ChronoField.SECOND_OF_DAY)); // gives 71461
System.out.println(time.getLong(ChronoField.EPOCH_DAY)); // gives 16105


что я хочу-это просто значение 1391539861 для локального datetime "04.02.2014 19:51:01".
Мой часовой пояс Europe/Oslo UTC+1 с переходом на летнее время.

623   5  

5 ответов:

классы LocalDate и LocalDateTime не содержат сведений о часовой пояс или смещение по времени, и секунды с эпохи были бы неоднозначными без этой информации. Однако объекты имеют несколько методов для преобразования их в объекты даты / времени с часовыми поясами, передавая ZoneId экземпляра.

LocalDate

LocalDate date = ...;
ZoneId zoneId = ZoneId.systemDefault(); // or: ZoneId.of("Europe/Oslo");
long epoch = date.atStartOfDay(zoneId).toEpochSecond();

LocalDateTime

LocalDateTime time = ...;
ZoneId zoneId = ZoneId.systemDefault(); // or: ZoneId.of("Europe/Oslo");
long epoch = time.atZone(zoneId).toEpochSecond();

'Millis since unix epoch' представляет собой мгновение, поэтому вы должны использовать мгновенный класс:

private long toEpochMilli(LocalDateTime localDateTime)
{
  return localDateTime.atZone(ZoneId.systemDefault())
    .toInstant().toEpochMilli();
}

преобразование, которое вам нужно, требует смещения от UTC / Greewich или часового пояса.

если у вас есть смещение, есть выделенного метода on LocalDateTime для этой задачи:

long epochSec = localDateTime.toEpochSecond(zoneOffset);

если у вас есть только ZoneId затем вы можете получить ZoneOffset С ZoneId:

ZoneOffset zoneOffset = ZoneId.of("Europe/Oslo").getRules().getOffset(ldt);

но вы можете найти конвертацию через ZonedDateTime проще:

long epochSec = ldt.atZone(zoneId).toEpochSecond();

посмотреть этот метод чтобы увидеть, какие поля поддерживаются. Вы найдете для LocalDateTime:

•NANO_OF_SECOND 
•NANO_OF_DAY 
•MICRO_OF_SECOND 
•MICRO_OF_DAY 
•MILLI_OF_SECOND 
•MILLI_OF_DAY 
•SECOND_OF_MINUTE 
•SECOND_OF_DAY 
•MINUTE_OF_HOUR 
•MINUTE_OF_DAY 
•HOUR_OF_AMPM 
•CLOCK_HOUR_OF_AMPM 
•HOUR_OF_DAY 
•CLOCK_HOUR_OF_DAY 
•AMPM_OF_DAY 
•DAY_OF_WEEK 
•ALIGNED_DAY_OF_WEEK_IN_MONTH 
•ALIGNED_DAY_OF_WEEK_IN_YEAR 
•DAY_OF_MONTH 
•DAY_OF_YEAR 
•EPOCH_DAY 
•ALIGNED_WEEK_OF_MONTH 
•ALIGNED_WEEK_OF_YEAR 
•MONTH_OF_YEAR 
•PROLEPTIC_MONTH 
•YEAR_OF_ERA 
•YEAR 
•ERA 

поле INSTANT_SECONDS - конечно-не поддерживается, потому что a LocalDateTime не может ссылаться на какие-либо абсолютного (глобального) времени. Но что полезно это поле EPOCH_DAY которая подсчитывает количество прошедших дней, начиная с 1970-01-01. Подобные мысли справедливы для типа LocalDate (С еще менее поддерживаемыми полями).

если вы намерены получить несуществующее поле millis-since-unix-epoch вам также нужен часовой пояс для преобразования из локального в глобальный тип. Это преобразование может быть сделано гораздо проще, см. Другие SO-posts.

возвращаясь к вашему вопросу и цифры в коде:

The result 1605 is correct
  => (2014 - 1970) * 365 + 11 (leap days) + 31 (in january 2014) + 3 (in february 2014)
The result 71461 is also correct => 19 * 3600 + 51 * 60 + 1

16105L * 86400 + 71461 = 1391543461 секунд с 1970-01-01T00: 00 :00 (внимание, без часового пояса) Затем вы можете вычесть смещение часового пояса (следите за возможным умножением на 1000 если в миллисекундах).

обновление после заданной информации о часовом поясе:

local time = 1391543461 secs
offset = 3600 secs (Europe/Oslo, winter time in february)
utc = 1391543461 - 3600 = 1391539861

как JSR-310-код с двумя эквивалентными подходами:

long secondsSinceUnixEpoch1 =
  LocalDateTime.of(2014, 2, 4, 19, 51, 1).atZone(ZoneId.of("Europe/Oslo")).toEpochSecond();

long secondsSinceUnixEpoch2 =
  LocalDate
    .of(2014, 2, 4)
    .atTime(19, 51, 1)
    .atZone(ZoneId.of("Europe/Oslo"))
    .toEpochSecond();

преобразование из человек читаемый дата эпохи:

long epoch = new java.text.SimpleDateFormat("MM/dd/yyyyHH:mm:ss").parse("01/01/1970 01:00:00").getTime() / 1000;

преобразование из эпоха до читаемой человеком даты:

String date = new java.text.SimpleDateFormat("MM/dd/yyyyHH:mm:ss").format(new java.util.Date (epoch*1000));

для другого языка конвертер: https://www.epochconverter.com

Comments

    Ничего не найдено.