Сложность форматирования дат в Groovy - PullRequest
2 голосов
/ 08 марта 2019

У меня проблемы с форматированием дат в Groovy.Я пытаюсь преобразовать строку обратно в локальную дату, и она не воспринимает ее так хорошо ...

DateTimeFormatter formatDates = DateTimeFormatter.ofPattern("yyyy-MM-dd hh:mm");

LocalDate currentLocalDate = LocalDate.now();
// modify the local date to the previous day
LocalDate previousDateLocalDate = currentLocalDate.minusDays(1)
// cast localdates to strings
String startDateString = previousDateLocalDate.toString() + " 00:00"
String endDateString = previousDateLocalDate.toString() + " 23:59"
// cast strings to localdates
LocalDate startDateLocalDate = LocalDate.parse(startDateString, formatDates);

Вывод показывает только то, что было в переменной previousDateLocalDate: 2019-03-06

Я не уверен, почему он падает чч: мм.Это может быть мой формат или мой синтаксис неправильный.Любые идеи очень приветствуются.Возможно ли, когда я вычитаю выходной из моего текущего дня, чтобы просто отформатировать его так, как мне нужно, чтобы он был там, или установить формат при создании LocalDate.now ()?

-Спасибо

Редактировать 1: Позвольте мне также добавить, что minusDays могут отличаться, так что может быть лучший способ получить предыдущий день до вчерашнего дня, но в некоторых случаях это может быть 7, 11 и т. Д.

Ответы [ 2 ]

1 голос
/ 08 марта 2019

Укажите часовой пояс явно

При вызове now вы всегда должны явно указывать желаемый / ожидаемый часовой пояс. В любой момент времени дата меняется по всему земному шару в зависимости от часового пояса. Это может быть «завтра» в Токио, Япония, а «вчера» в Касабланке, Марокко. Когда вы опускаете зону, текущая зона по умолчанию JVM неявно применяется во время выполнения - поэтому ваши результаты могут отличаться.

ZoneId z = ZoneId.of( "Africa/Casablanca" ) ;     // Or `ZoneId.systemDefault` if you actually want the JVM’s current default time zone.
LocalDate ld = LocalDate.now( z ) ;               // Capture the current date as seen in the wall-clock time used by the people of a particular region (a time zone). 

LocalDate

LocalDate класс представляет только дату, без времени суток и без часового пояса или смещения от UTC.

Если вы хотите объединить время суток с датой, используйте один из других классов.

table showing modern versus legacy classes used to represent a moment

Дата-время математика

Классы java.time предлагают plus… и minus… методы для добавления или вычитания промежутка времени.

LocalDate yesterday = ld.minusDays( 1 ) ;

Первый момент дня

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

ZonedDateTime zdt = ld.atStartOfDay( z ) ;        // Let java.time determine the first moment of the day.

Half-Open

Очевидно, вы хотите, чтобы конец дня. Отслеживание последнего момента дня проблематично. Например, ваш текст 23:59 пропустит любой момент этой последней минуты дня.

Как правило, лучшим подходом к отслеживанию промежутков времени является подход Half-Open, где начало включительно , а окончание эксклюзив . Таким образом, день начинается с первого момента дня и продолжается, но не включает первый момент следующего дня.

ZonedDateTime start = ld.atStartOfDay( z ) ;               // Start of today.
ZonedDateTime stop = ld.plusDays( 1 ).atStartOfDay( z ) ;  // Start of tomorrow.

DateTimeFormatter

Чтобы сгенерировать строки, представляющие значение объекта даты и времени, используйте объект DateTimeFormatter. Я не буду описывать это здесь, так как это было уже много-много раз уже в переполнении стека.

DateTimeFormatter f = DateTimeFormatter.ofPattern( "uuuu-MM-dd HH:mm" ) ;
String output = zdt.format( f ) ;      // Generate text representing the value of this `ZonedDateTime` object.

Имейте в виду, что объекты даты и времени не имеют «формата», формат имеет только текстовое представление значения объекта даты и времени. Не связывайте строковый объект с объектом даты и времени. Объект даты и времени может анализировать строку и может генерировать строку, но сам по себе не является строкой.

0 голосов
/ 08 марта 2019

попробуйте этот инструмент

import grails.gorm.transactions.Transactional
import org.springframework.stereotype.Component

import java.time.LocalDate
import java.time.Period
import java.time.ZoneId
import java.time.chrono.ChronoLocalDate
import java.time.chrono.Chronology
import java.time.chrono.MinguoChronology
import java.time.format.DateTimeFormatter
import java.time.format.DateTimeFormatterBuilder
import java.time.format.DecimalStyle
import java.time.temporal.TemporalAccessor
import java.time.temporal.TemporalAdjusters
    Date mgStringToDate(String mgString, String separator = "/") {

        if(mgString){
            Locale locale = Locale.getDefault(Locale.Category.FORMAT);
            Chronology chrono = MinguoChronology.INSTANCE;
            DateTimeFormatter df = new DateTimeFormatterBuilder().parseLenient()
                    .appendPattern("yyy${separator}MM${separator}dd").toFormatter().withChronology(chrono)
                    .withDecimalStyle(DecimalStyle.of(locale));
            TemporalAccessor temporal = df.parse(mgString);
            ChronoLocalDate cDate = chrono.date(temporal);
            Date date = Date.from(LocalDate.from(cDate).atStartOfDay(ZoneId.systemDefault()).toInstant());
            return date
        }else{
            return null
        }
    }

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...