2

Here in Washington DC, on November 3rd 2019 at 2:00 am the clock was "moved back" to 1:00 am.

This means the local time was like this:

=== Nov 2nd ===:=== Nov 3rd ===========
               :                        
   9   10  11  12  1   2
---+---+---+---+---+-*-+
               :   +-#-+---+---+---+---
               :   1   2   3   4   5

So, if an accident happened at 1:30 am, when I record it, it should be clear if it happened on first time line (the * there) or the second one (the # there). This is quite important to establish responsibilities and other legal liabilities.

When looking at the java.time.LocalDateTime it doesn't seem to include the time line in it. Was this intentional, or an oversight?

If the time line is not included, is there a better Java class to store the local date/time?

The Impaler
  • 45,731
  • 9
  • 39
  • 76
  • 2
    Sounds like you want a `ZonedDateTime` – k5_ Mar 18 '20 at 14:26
  • LocalDateTime explicitly states "This class does not store or represent a time-zone. Instead, it is a description of the date, as used for birthdays, combined with the local time as seen on a wall clock. It cannot represent an instant on the time-line without additional information such as an offset or time-zone. " - If you need time-zone information you should probably use ZonedDateTime instead – OH GOD SPIDERS Mar 18 '20 at 14:26
  • @OHGODSPIDERS But the "wall clock" showed 1:30 am... two times. – The Impaler Mar 18 '20 at 14:28
  • I don't understand what you are getting at here.. Yes it did and just like the class LocalDateTime without any additiional Information (Timezone) you are unable to differentiate between those 2 times of showing 1:30. But since you want to you need to use a class that has that extra information: the already mentioned ZonedDateTime – OH GOD SPIDERS Mar 18 '20 at 14:30
  • @OHGODSPIDERS just out of interest, which `ZoneId` should OP use for that? `"EST"` maps to UTC-5 without considering daylight saving times... – deHaar Mar 18 '20 at 14:39
  • 1
    [Duplicate](https://stackoverflow.com/questions/32833896/does-java-8s-new-java-date-time-api-take-care-of-dst). [Tutorial](https://www.baeldung.com/java-daylight-savings) – y_ug Mar 18 '20 at 14:39
  • @deHaar [According to time.is](https://time.is/Washington,_D.C.#time_zone), the time zone for Washington DC is `America/New_York`. – Basil Bourque Mar 18 '20 at 15:03
  • @BasilBourque Thanks, I found that out myself (even at the mentioned website) before I posted the answer. But it took me some time, admittedly... – deHaar Mar 18 '20 at 15:06

1 Answers1

3

Use a ZonedDateTime as already suggested in a comment, you can try it with a base time and add some minutes in order to see the result, like this:

public static void main(String[] args) {
    // let's take a base time of 1:30 in EST (with daylight saving)
    ZonedDateTime nov3rd2019OneThirtyAM = ZonedDateTime
            .of(2019, 11, 3, 1, 30, 0, 0, ZoneId.of("America/New_York"));
    // add 10 minutes 10 times and print the result each time
    for (int i = 0; i < 100; i += 10) {
        System.out.println(nov3rd2019OneThirtyAM.plusMinutes(i));
    }
}

Output is this (check the part where 10 minutes are added to 1:50, there are 2 of them):

2019-11-03T01:30-04:00[America/New_York]
2019-11-03T01:30-04:00[America/New_York]
2019-11-03T01:40-04:00[America/New_York]
2019-11-03T01:50-04:00[America/New_York]
2019-11-03T01:00-05:00[America/New_York]
2019-11-03T01:10-05:00[America/New_York]
2019-11-03T01:20-05:00[America/New_York]
2019-11-03T01:30-05:00[America/New_York]
2019-11-03T01:40-05:00[America/New_York]
2019-11-03T01:50-05:00[America/New_York]
2019-11-03T02:00-05:00[America/New_York]
deHaar
  • 17,687
  • 10
  • 38
  • 51
  • 1
    Didn't want to use a "world" date time class (like `ZonedDateTime` or `OffsetDateTime`) but I guess it's wise to do it, because all legal consequences. I still feel like the `LocalDateTime` class is incomplete, though (but that's just me). +1 – The Impaler Mar 18 '20 at 14:51
  • 1
    @TheImpaler I understand it feels somehow incomplete, but it's the design and its good, maybe not perfect, but imagine having to do that with `Date` and `Calendar`... – deHaar Mar 18 '20 at 14:53
  • 4
    @TheImpaler The `LocalDateTime` class represents only a date and a time-of-day without the context of time zone or offset-from-UTC (a number of hours-minutes-seconds). So this class cannot represent a moment, is not a point on the timeline. To represent a moment, use `Instant`, `OffsetDateTime`, `ZonedDateTime`. See the Question, [*What is the difference between Instant and LocalDateTime?*](https://stackoverflow.com/q/32437550/642706). – Basil Bourque Mar 18 '20 at 14:57
  • @BasilBourque "...is not a point on the timeline" -- It seems that LocalDateTime represent a fictional calendar (if I may say so) that accounts for most days, but not all of them. Thanks, this has made me think. I think I'll better stay away from this class, for the time being, until I understand it better. – The Impaler Mar 18 '20 at 15:06
  • 1
    @TheImpaler I think you are overthinking this. LocalDateTime is a class that is specifically designed without any Timezone information for when you don't need it and when having a Timezone would just be confusing and wrong. Imaging you would have to save when New Year starts but you only had Java DateTime classes that also require you to supply a Timezone. What Timezone would you set here? After all newe year cannot be specified as beeing "0:00 UTC+0" because New year doesn't happen at the same instant all over the world. Instead it happens at 0:00 of the Local Time. Hence LocalDateTime. – OH GOD SPIDERS Mar 18 '20 at 15:11
  • @TheImpaler I will call you tomorrow March 19th 2020 at noon. Do you know when to expect the call? No. Without the context of a time zone or offset-from-UTC, you have almost no idea when the phone will ring. That is a `LocalDateTime`. To clarify, I message “I will call you tomorrow March 19th 2020 at noon in time zone `Africa/Casablanca`”. That is a `ZonedDateTime`. Do you know when to expect the call? Yes, you know the very moment:. `ZonedDateTime.of( 2020 , 3 , 19 , 12 , 0 , 0 , 0 , ZoneId.of( "Africa/Casablanca" ) ).withZoneSameInstant( ZoneId.of( "America/New_York" ) )` → 7 AM in DC. – Basil Bourque Mar 18 '20 at 19:34
  • @BasilBourque I'm with you. Just for the sake of a philosophical discussion, with no consequences whatsoever in the real world: After really thinking about this, it seems my [very personal] confusion stems from the name of the class itself: LocalDateTime. I now understand it represents the local datetime in the pre-20th century clocks (DST implemented in 1905?) and as such may not to be that useful to represent values in today's world. Maybe it would be more accurate to name it "BelleEpoqueDateTime" or similar (pardon the audacity). Writing this helped me to clarify my thoughts. Thanks again. – The Impaler Mar 18 '20 at 20:21
  • 1
    @TheImpaler Nope, not quite right. `LocalDateTime` has nothing to with Daylight Saving Time (DST) nor modern history of the last century or two. A `LocalDateTime` is simply a date and a time-of-day, nothing more, nothing less. Internally the class keeps a count of seconds since the arbitrary reference point of 1970-01-01 00:00, plus a count of nanoseconds as a fractional second. Dates are calculated from that count by assuming days of exactly 24-hours length. The name is confusing, but I’ve seen none better. Regard the word “local” as meaning *any* locality but not any particular locality. – Basil Bourque Mar 18 '20 at 22:19