cnuernber / dtype-next

A Clojure library designed to aid in the implementation of high performance algorithms and systems.
Other
339 stars 21 forks source link

Feature request: human readable datetime #9

Closed ashimapanjwani closed 3 years ago

ashimapanjwani commented 3 years ago

Hi Chris! Ashima here. I have been using your library in my project and would like to thank you for creating such a wonderful tool. Just wanted to raise a feature request. While using the date-time functionality, I have noticed some differences in the way it renders in Clojure vs R. The dates in R seem to be prettier and in a much more human readable format. Would love to see something similar in Clojure. I have added code samples comparing the two in case you would like to check it out.

Clojure

(tablecloth/dataset {:x (dtype-dt/local-date-time)})

clj꞉r4ds-in-clj.wrangle.01-tibbles꞉> 
_unnamed [1 1]:

|                         :x |
|----------------------------|
| 2021-01-08T00:45:39.821804 |

R

lubridate::now()

[1] "2021-01-08 00:47:59 IST"

Note: The version of Tablecloth that I'm using is [scicloj/tablecloth "5.00-beta-21a"]

Thank you for your time :)

cnuernber commented 3 years ago

@ashimapanjwani - Thanks for bringing this up; it would be nice to have better datetime displays!

Currently datatype uses the java 'toString' method for displaying objects to the repl. If you create a java.time.LocalDateTime and call it's tostring method you will see it is the same.

It appears that you are also comparing two different things. A local date time has no time zone. This is one of the aspects of java.time that is tough to understand.

The java.time progression is something like:

instant + offset or timezone -> zoned-date-time zoned-date-time - offset or timezone -> local-date-time local-date-time - time -> local-date

Instants are grounded in epoch times. As are zoned datetimes. Local date times are not 'grounded' and require a timezone to move to universal or epoch date-times.

The direct comparison would be a zoned-date-time as your lubridate result contains a timezone. I think you will find this also doesn't print the same as R but it contains the same information:

user> (require '[tech.v3.datatype.datetime :as dtype-dt])
nil
user> (dtype-dt/instant)
#object[java.time.Instant 0x66987ed6 "2021-01-08T16:52:30.503Z"]
user> (println (.toString *1))
2021-01-08T16:52:30.503Z
nil
user> (dtype-dt/zoned-date-time)
#object[java.time.ZonedDateTime 0x476dbcfb "2021-01-08T09:52:57.525-07:00[America/Denver]"]
user> (println (.toString *1))
2021-01-08T09:52:57.525-07:00[America/Denver]
nil
user> (require '[tech.v3.dataset :as ds])
nil
user> ;;Importantly, the types can parse their tostring representations.
user> (java.time.ZonedDateTime/parse "2021-01-08T09:52:57.525-07:00[America/Denver]")
#object[java.time.ZonedDateTime 0x64b0b2ec "2021-01-08T09:52:57.525-07:00[America/Denver]"]
user> (ds/->dataset {:local-date [(dtype-dt/local-date)]
                     :local-date-time [(dtype-dt/local-date-time)]
                     :zoned-date-time [(dtype-dt/zoned-date-time)]
                     :instant [(dtype-dt/instant)]})
_unnamed [1 4]:

| :local-date |        :local-date-time |                              :zoned-date-time |                 :instant |
|-------------|-------------------------|-----------------------------------------------|--------------------------|
|  2021-01-08 | 2021-01-08T10:00:26.365 | 2021-01-08T10:00:26.365-07:00[America/Denver] | 2021-01-08T17:00:26.365Z |

Now, back to your original point - R's print method seems cleaner to you -

Undoubtedly this is true for you and perhaps it is globally true - R has excellent printing of many things. Perhaps we could work on a system by which users can set the library's formatting function for datetime objects in general?

I have also found that the default java representation of the datetimes is at times confusing. A possible solution would be to add some global state and have custom formatters here. Similarly we could add metadata arguments that change the formatting on a datatype-specific basis.

ashimapanjwani commented 3 years ago

@cnuernber Thanks for the clear explanation of the difference between instant, zoned-date-time, and local-date-time. It cleared up a lot of my doubts. The solution that you suggested sounds interesting and maybe I'll be able to work on a PR for that.

cnuernber commented 3 years ago

Closing this for now. We can revisit if someone has time to address this meaningfully.