java 如何将 LocalDateTime 转换为 GregorianCalendar?

声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow 原文地址: http://stackoverflow.com/questions/38823460/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me): StackOverFlow

提示:将鼠标放在中文语句上可以显示对应的英文。显示中英文
时间:2020-11-03 03:48:41  来源:igfitidea点击:

How to convert LocalDateTime to GregorianCalendar?

javajava-time

提问by membersound

Why is it possible to pass a LocalDateTimeobject into the ZonedDateTime.from()method, if it's not possible to parse a simple DateTime, as follows?

如果无法解析一个简单的,为什么可以将LocalDateTime对象传递给ZonedDateTime.from()方法,DateTime如下所示?

@Test
public void test() throws Exception {
    GregorianCalendar.from(ZonedDateTime.from(LocalDateTime.parse("2016-08-31T23:00:59")));
}

Result:

结果:

java.time.DateTimeException: Unable to obtain ZonedDateTime from TemporalAccessor: 2016-08-31T23:00:59 of type java.time.LocalDateTime
    at java.time.ZonedDateTime.from(ZonedDateTime.java:565)

回答by Unknown

Why is it possible to pass a LocalDateTime object into the ZonedDateTime.from() method if it's not possible to parse a simple datetime?

如果无法解析简单的日期时间,为什么可以将 LocalDateTime 对象传递给 ZonedDateTime.from() 方法?

Both LocalDateTimeand ZonedDateTimeimplement the interface called Temporal, which extends TemporalAccessor.

双方LocalDateTimeZonedDateTime实现所谓的接口Temporal,它扩展TemporalAccessor

LocalDateTimeis datetime withouta time-zone in the ISO-8601 calendar system, such as 2007-12-03T10:15:30

LocalDateTime是ISO-8601 日历系统中没有时区的日期时间,例如 2007-12-03T10:15:30

ZonedDateTimeis datetime witha time-zone in the ISO-8601 calendar system, such as 2007-12-03T10:15:30+01:00 Europe/Paris.

ZonedDateTime带有ISO-8601 日历系统中时区的日期时间,例如 2007-12-03T10:15:30+01:00 Europe/Paris。

Now, if you see the implementation of from(TemporalAccessor temporal)method that is expecting the TemporalAccessor… Both LocalDateTimeand ZonedDateTimeimplements the method of super interface TemporalAccessor(Temporal extends TemporalAccessor), which is normal (i.e. has a polymorphic behavior) to allow us to pass both the local as well as zoned datetime.

现在,如果你看到的实现from(TemporalAccessor temporal)方法是期待TemporalAccessor......都LocalDateTimeZonedDateTime农具超接口的方法TemporalAccessorTemporal extends TemporalAccessor),这是正常的(即具有多态),使我们能够同时通过本地和分区日期时间。

Code:

代码:

public static ZonedDateTime from(final TemporalAccessor temporal) {
            if (temporal instanceof ZonedDateTime) {
                return (ZonedDateTime) temporal;
            }

            try {
                final ZoneId zone = ZoneId.from(temporal);

                if (temporal.isSupported(INSTANT_SECONDS)) {
                    long epochSecond = temporal.getLong(INSTANT_SECONDS);
                    int nanoOfSecond = temporal.get(NANO_OF_SECOND);
                    return create(epochSecond, nanoOfSecond, zone);
                } else {
                    LocalDate date = LocalDate.from(temporal);
                    LocalTime time = LocalTime.from(temporal);
                    return of(date, time, zone);
                }
            } catch (final DateTimeException ex) {
                throw new DateTimeException("Unable to obtain ZonedDateTime from TemporalAccessor: " +
                        temporal + " of type " + temporal.getClass().getName(), ex);
            }
        }

Now, we come to your problem.

现在,我们来解决您的问题。

You are passing LocalDateTime.parse("2016-08-31T23:00:59")to the from(TemporalAccessor temporal)method. So, the temporal is not an instance of ZonedDateTime, it comes ZoneId zone = ZoneId.from(temporal);.

您正在传递LocalDateTime.parse("2016-08-31T23:00:59")给该from(TemporalAccessor temporal)方法。因此,时间不是 的实例ZonedDateTime,而是ZoneId zone = ZoneId.from(temporal);

So, your are getting the error since the LocalDateTimedoes not contain the timezone.

因此,您收到错误,因为LocalDateTime不包含时区。

How to solve the issue?

如何解决问题?

Use the Zone ID with the ZonedDateTime:

将区域 ID 与ZonedDateTime

LocalDateTime ldt = LocalDateTime.parse("2016-08-31T23:00:59");
ZoneId zoneId = ZoneId.of("Europe/Paris");
ZonedDateTime zdt = ldt.atZone(zoneId);
GregorianCalendar gc = GregorianCalendar.from(zdt);

with JUnit test

使用 JUnit 测试

@Test
public void test() throws Exception {
    ZoneId zoneId = ZoneId.of("Europe/Paris");
    GregorianCalendar.from(LocalDateTime.parse("2016-08-31T23:00:59").atZone(zoneId));
}

回答by Ramachandran.A.G

You will have to provide the ZoneIdas well. I will have to look up on the behavior as to why this is. I will edit and post as soon as I see it.

您还必须提供ZoneId。我将不得不调查这种行为的原因。我一看到就会编辑和发帖。

LocalDateTime ldt = LocalDateTime.parse("2016-08-31T23:00:59");
GregorianCalendar gc = GregorianCalendar.from(ZonedDateTime.of(ldt, ZoneId.systemDefault()));
System.out.println(gc);

This results:

结果如下:

java.util.GregorianCalendar[time=1472664659000,areFieldsSet=true,areAllFieldsSet=true,lenient=true,zone=sun.util.calendar.ZoneInfo[id="Asia/Calcutta",offset=19800000,dstSavings=0,useDaylight=false,transitions=6,lastRule=null],firstDayOfWeek=2,minimalDaysInFirstWeek=4,ERA=1,YEAR=2016,MONTH=7,WEEK_OF_YEAR=35,WEEK_OF_MONTH=5,DAY_OF_MONTH=31,DAY_OF_YEAR=244,DAY_OF_WEEK=4,DAY_OF_WEEK_IN_MONTH=5,AM_PM=1,HOUR=11,HOUR_OF_DAY=23,MINUTE=0,SECOND=59,MILLISECOND=0,ZONE_OFFSET=19800000,DST_OFFSET=0]

Edits:Just came across this interesting thread...

编辑:刚刚遇到这个有趣的线程......

The Java 8 java.time.* package is a very strict package. It doesn't allow flexibility between types and inputs - if you want a ZonedDateTime object, you must construct it from an input that has a time zone, a date & a time.

Java 8 java.time.* 包是一个非常严格的包。它不允许类型和输入之间的灵活性 - 如果您想要 ZonedDateTime 对象,则必须从具有时区、日期和时间的输入构建它。