Well, as the title says. I needed a date library for a small D project I'm working. I tried to use the Gregorian.d module that Andrei started, but as it was just a simple draft, it lacked a lot of content.

And as Boost's date_time was the basis for Andrei's work, and I had prior experience working with this library, I tried to implement almost all of what was needed to have a working Date struct, as documented here:

http://www.boost.org/doc/libs/1_42_0/doc/html/date_time/gregorian.html

The only concrete date types that I didn't implemented were some ranges (converted from C++ iterators) to iterate Dates on monthly and yearly basis. Everything else is there in one way or another. Now, the original Boost library is quite complex and comprehensive (I'm talking about the Date facilities, I didn't even tried to implement time, LocalDate, TimeZones and string conversion), so I had to do some compromises in order to at least finish the module. So here are some of the things I didn't implemented:

- There's no notion of +infinites and -infinites. The only special value supported is Not A Date. This because if I wanted to support infinities, I had to implement a big and complex struct that emulates a integer with support to IEEE754 NAN and infinites. This can be done, but it would make the gregorian.d module even bigger.

- The integer type used internally for doing the calculations is int, and cannot be changed at compile time. I didn't know how to propagate the same integer type across all the different date structures and functions, without doing the template instantiation each time the user need a Date instance.

- There's no way to change the granularity of the Date structure. The minimal unit used is days. But as this is how was originally implemented, I don't think it's a bad decision (sorry Michel Fortin).

- The calendar used is Gregorian, and there's no way to change it to another (like Julian, ISO8601, Coptic, etc.). Almost all the calculations are done internally by the Date class. This is because, first, I followed the model Andrei used, and second, almost everyone and his mother use Gregorian. Is de facto standard. :p

- There are not ranges to iterate using months or years as units. Again, for implementing this, I would have to implement yet another internal structure that emulates a wrapping integer with arbitrary upper and lower bounds. This structure is quite big too, so I would bloat even more the module.

- The work I did is kinda shoddy and amateurish. :D I used a lot of properties (@safe), pure and nothrow, I overdid with the comments and the unittest, I don't get ranges quite well yet, etc. I don't expect the module to be used as is, but more like something that a more experienced programmer can copy and improve to make a better gregorian module.

And just to be clear: This module contains only the implementation of the Date struct and friends (ranges, DateRange, DayCount, etc), so no time, UTC support, only basic ISO8601 support, no local time, or time zones, no complex conversion to strings and parsing etc. See http://www.boost.org/doc/libs/1_42_0/doc/html/date_time/gregorian.html if you want to have a small idea of what's implemented.

Oh, I almost forgot, the code is here: http://ideone.com/SCR34

Apologies for this tl;dr; wall of text. And I'm eagerly awaiting some comments, critics and ideas to improve this work.

Thanks.


--
Yao G.

Reply via email to