Create Instant using a negative year

被刻印的时光 ゝ 提交于 2019-12-10 19:51:26

问题


I am trying to create an Instant based upon a B.C.E. year in the Gregorian calendar.

Here is what I have so far:

Instant.FromDateTimeOffset(new DateTimeOffset(-1000, 10, 01,
                                              0, 0, 0, 0,
                                              new System.Globalization.GregorianCalendar(),
                                              new TimeSpan()));

I get the error:

An unhandled exception of type 'System.ArgumentOutOfRangeException' occurred in mscorlib.dll Additional information: Year, Month, and Day parameters describe an un-representable DateTime.

Edit

Doing some research on NodaTime, I can see that it does have the ability to represent the dates I want, as it can accept negative ticks from the Unix epoch:

The Noda Time Instant type represents a point on this global timeline: the number of ticks which have elapsed since the Unix epoch. The value can be negative for dates and times before 1970 of course - the range of supported dates is from around 27000 BCE to around 31000 CE in the Gregorian calendar. - http://nodatime.org/1.3.x/userguide/concepts.html

So I would like to know how to do this using NodaTime rather than create my own implementation, as is mentioned here for instance.


回答1:


The correct way to create a BCE date in Noda Time is like this:

LocalDate date = new LocalDate(Era.BeforeCommon, 1000, 10, 1);

This gives a LocalDate object, which is representative of just having a date. You asked for an Instant, which represents an exact point in time. These are two very different concepts.

In order to get an Instant from a LocalDate, one has to make a few assertions:

  1. What time of day did it occur?
  2. What time zone was it in?
  3. Is the time valid and unambiguous on that date within that zone?

Let's pick midnight for the time and UTC for the time zone:

Instant instant = date.AtMidnight().InUtc().ToInstant();

Since we chose UTC, we didn't have to address the valid/unambiguous question. With other zones, we would use one of the InZone methods instead of InUtc.

Also - you can indeed create an Instant directly (as Caramiriel showed), but be careful. Year 1 BCE is represented by year 0, so if you want 1000 BCE, you'd have to pass -999, not -1000.

Instant instant = Instant.FromUtc(-999, 10, 1, 0, 0, 0);

Again, this assumes the time at midnight and the UTC time zone.

Finally, keep in mind that none of these calendar systems or time zones actually existed during that time period, and usually when working with dates so old, the time part is not very accurate or relevant. Therefore, I recommend you attempt to only work in terms of LocalDate objects, and not use Instant at all, if you can.



来源:https://stackoverflow.com/questions/32353262/create-instant-using-a-negative-year

标签
易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!