[Haskell-cafe] Can't do basic time operations with System.Time

Simon Marlow simonmar at microsoft.com
Fri Jan 21 08:56:23 EST 2005


On 20 January 2005 22:12, John Goerzen wrote:

> I have a simple desire.  I have a string that I need to parse as a
> date/time string in the local timezone, then convert it to standard
> seconds-since-epoch format.  This is trivial in C, Perl, Python, etc.
> but seems impossible to do reliably in Haskell.  I'm hoping someone
> can tell me where I've gone wrong.
> 
> My initial idea was to parse the string, generate a CalendarTime
> object, use toClockTime to convert it to seconds-since-epoch, and
> then grab the value out of that.  There were some problems, though:
> what to put in ctTZ and ctIsDST?  I initially loaded them with 0 and
> False, though that turned out to be clearly wrong.
>
> My next idea was to take the ctTZ result from toCalendarTime, then use
> that for all the CalendarTime objects I'd generate.  That was wrong,
> too, during daylight savings time.  I don't think I should have to
> re-implement the algorithms for determining whether a given date is
> under DST worldwide.
> 
> What I really need is just a wrapper around mktime() that just calls
> mktime and doesn't do anything else.  All the post-processing that
> System.Time is doing is what's causing me trouble.  I'd just like it
> to ignore ctTZ, ctTZName, and ctIsDST.  That would yield behavior
> identical to the C library.

If you set ctTZ to the UTC offset outside DST, and set ctIsDST to False,
then toClockTime will do the DST calculation for you.

ctTZ is the actual UTC offset (ie. it is adjusted for DST).  Hence,
toClockTime ignores ctIsDST when performing the conversion: it isn't
necessary.

I can't tell what's wrong here, if anything (general brokenness in the
System.Time API notwithstanding).  Ah *lightbuilb* - I think I see: you
want to take a calendar time without any TZ information, assume it is a
time at the current geographical location, and produce a CalendarTime
for that.  Hmm, it looks like the current API doesn't support that -
toClockTime assumes you know the timezone.  That's a shame.

There's one way that's almost correct: take your initial calendar time,
set ctTZ to your non-DST UTC offset, then call toClockTime and
toCalendarTime on the result, and you'll get an appropriate ctTZ for
that time.  Plug the new ctTZ into the original time, and toClockTime
again (you can shortcut this by adjusting the ClockTime directly).  I'll
leave it up to you how to handle the boundaries properly :-)

Cheers,
	Simon


More information about the Haskell-Cafe mailing list