www.digitalmars.com         C & C++   DMDScript  

digitalmars.D - datetime review part 2

As some of you know, I've been working on a datetime module for possible 
inclusion in Phobos, and I posted the initial code for review on the Phobos
about a week ago. I have updated the code per the suggestions in that thread. 
Andrei requested that I move the review to the main D list, so I'm posting my 
code here this time around. The code and html documentation can be found in
compressed tar file here: http://is.gd/g6em1

It is intended to replace std.date and the nascent std.datetime. The code 
currently in std.datetime has already been integrated into my code.

My datetime module is modeled after Boost's date/time API but does not use any 
of its code. I've attempted to D-ify it in various ways (including making it
ranges instead of iterators), but the API is still fairly close to Boost's. One 
of the big differences from Boost is that I removed the special time points 
(posifitive infinity, negative infinity, and invalid), since they complicated
code considerably and didn't help at all with infinite ranges, since infinite 
ranges must be known to be infinite at compile time whereas Boost determines 
infinity based on the end points (which are only known at runtime). I also made 
it so the the interval and duration types are generic, so you don't have to
with different types of intervals and durations depending on the type of the

The major time point types are Date, TimeOfDay, DateTime, and SysTime. Date, 
TimeOfDay, and DateTime are optimized for calendar-based operations and have no 
concept of time zone, whereas SysTime is used for the system time and does have 
a time zone but is not optimized for calendar-based operations. SysTime holds 
the time in hecto-nanoseconds (100 ns) from midnight, January 1st 1 A.D. UTC 
which avoids all conversion errors due to DST (conversions to the time zone for 
the SysTime is done in the getters). All date types use the Proleptic Gregorian 
Calendar (so they use the Gregorian leap year calculations for their whole 
length) and use year 0 for 1 B.C. as per ISO 8601. Unlike Boost, they cover
tens-of-thousands of years B.C. to tens-of-thousands of years A.D. (the exact 
range depending on the type) instead of just some subset of A.D. dates.

When using SysTime, you can ignore time zones if you wish (in most places, 
LocalTime is used if no TimeZone object is given), but you can also specificy 
which time zone to use. LocalTime implements local time, UTC implements UTC, 
SimpleTimeZone allows you to construct a time zone with an offset from UTC but
DST, and PosixTimeZone and WindowsTimeZone allow you to select arbitrary time 
zones on posix and windows systems respectively (you can also use PosixTimeZone 
on Windows if you provide the time zone database files). Unlike my first 
submission, PosixTimeZone is now complete, but WindowsTimeZone is still just 
stubbed out.

Durations have been simplified since my previous submission. There are now only 
two duration types: Duration and TickDuration (TickDuration being used by
stopwatch code and internally for getting the time, whereas Duration is used 
pretty much everywhere else). You can no longer have durations of months or 
years due to the issue of converting between months and smaller units (because 
months and years have a variable number of days). Rather, functions have been 
provided on the various types for handling months and years directly.

There are interval types (Interval, PosInfInterval, and NegInfInterval) for 
dealing with intervals (including positively and negatively infinite intervals) 
as well as corresponding range types. Ranges are constructed from an interval 
and range-generating function which generates each successive time point in a 
range (IRange and Interval's fwdRange() are good places to look for more
an that), so they are extremely flexible.

I have included a text file, changes.txt, which contains a list of the majority 
of changes that I've made since I last posted my code, so if you looked at the 
first round of code, it should give you a good idea of what has been changed.

The source files are in Src, and the html doc files are in Doc. I attempted to 
make the doc files look more like Phobos this time around, so I used a slight 
variation on std.ddoc (so that it looked for the css files in the same 
directory), and have included the css files with them, so they should be much 
easier to read (though honestly, the link list at the top of the page is 
horrible for this module, since it makes no attempt to split out module 
functions from struct or class functions, and many of the struct and class 
functions have the same name and yet only one of them gets listed).

Hopefully the documentation is enough to properly understand the module, and of 
course, the source is there to examine as well. So, review away.

- Jonathan M Davis
Oct 17 2010