难以格式化 Groovy 中的日期

Difficulty formatting dates in Groovy

我在格式化 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

我不确定为什么要删除 hh:mm。可能是我的格式问题还是我的语法错误。任何想法将不胜感激。当我从当天减去一天的休息时间以仅格式化它我需要它在那里而不是在我创建 LocalDate.now()?

时设置格式时是否有可能

-谢谢

编辑 1:我还要补充一点,minusDays 可能会有所不同,因此可能有更好的方法来获取前一天的前一天,但在某些情况下可能是 7、11 等...

明确指定时区

您应该在调用 now 时明确指定 desired/expected 时区。对于任何给定时刻,全球各地的日期因时区而异。在日本东京可能是“明天”,而在摩洛哥卡萨布兰卡可能是“昨天”。当您省略区域时,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 class 仅表示日期,没有时间,也没有时区或与 UTC 的偏移量。

如果您希望将时间与日期结合使用,请使用其他 classes 之一。

日期时间数学

java.time classes 提供了 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.

半开

显然你想要一天结束。跟踪当天的最后时刻是有问题的。例如,您的 23:59 文本将错过当天最后一分钟的任何时刻。

通常,一种更好的跟踪时间跨度的方法是半开方法,其中开始是 包含,而结尾是 不包含.所以一天从当天的第一刻开始,一直到但不包括第二天的第一刻。

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

DateTimeFormatter

要生成表示日期时间对象值的字符串,请使用 DateTimeFormatter 对象。我不会在这里介绍它,因为它已在 Stack Overflow 上 covered many many many times already

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

请记住,日期时间对象没有“格式”,只有日期时间对象值的文本表示才有格式。不要将字符串对象与日期时间对象混为一谈。日期时间对象可以解析字符串,生成字符串,但它本身不是字符串。

试试这个工具

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
        }
    }