Re: [R] diff, POSIXct, POSIXlt, POSIXt

From: Martin Maechler <maechler_at_stat.math.ethz.ch>
Date: Mon 24 Jul 2006 - 19:46:05 EST

>>>>> "Gabor" == Gabor Grothendieck <ggrothendieck@gmail.com> >>>>> on Sun, 23 Jul 2006 09:02:35 -0400 writes:

    Gabor> Moving this to r-devel.

[would have been a good idea ... but you didn't;  I think it's too late now; rather keep the msg thread together]

    Gabor> Looking at the diff.POSIXt
    Gabor> code we see the problem is that it takes the length
    Gabor> of the input using length which is wrong since in the
    Gabor> case of POSIXlt the length is always 9 (or maybe
    Gabor> length should be defined differently for POSIXlt?).

Though I agree with Spencer that a user may expect length() to behave differently, but I don't think this would be a good idea. Yes, length() is generic, but its help() emphasizes that for lists, length() should be the number of list elements. Of course anyone one *can* define length() methods that behave differently for his/her classes, but then one would also want to make sure that e.g. x[length(x)] or 'x[length(x)] <- value' works and -- in a case of simple S3 class built on a list, would work differently than if x was a the simple list.

In my view, I would only consider redefing length() for "non-basic" S4 classes, i.e. those with slots, where no confusion is possible, since these objects are definitely not simple vectors nor lists (aka "generic" vectors).

    Gabor> Try this which gives the same problem:

    Gabor> dts[-1] - dts[-length(dts)]

    Gabor> We get a more sensible answer if length is calculated     Gabor> correctly:

    Gabor> dts[-1] - dts[-length(dts[[1]])]

Yes, thanks Gabor, and thanks to Patrick who is right that this is a bug and diff() should work for both kinds of POSIXt objects. I'll fix this for both R-patched and R-devel - but not via redefining length(<POSIXlt>).

Martin Maechler, ETH Zurich

    Gabor> On 7/23/06, Patrick Giraudoux     Gabor> <patrick.giraudoux@univ-fcomte.fr> wrote:
>> > Try converting to POSIXct: That's what I did finally
>> (see the previous e-mail).
>>
>> dts<-c("15/4/2003","15/7/2003","15/10/2003","15/04/2004","15/07/2004","15/10/2004","15/4/2005","15/07/2005","15/10/2005","15/4/2006")
>>
>> dts <- as.POSIXct(strptime(dts, "%d/%m/%Y")) diff(dts)
>>
>> Time differences of 91, 92, 183, 91, 92, 182, 91, 92, 182
>> days
>>
>> > What is the problem you are trying to solve? Actually,
>> I don't understand why using diff() and POSIXct provides
>> the expected result and not using POSIXlt. Both POSIXct
>> and POSIXlt are of class POSIXt. The doc of diff()
>> stresses that <'diff' is a generic function with a
>> default method and ones for classes '"ts"', '"POSIXt"'
>> and '"Date"'>. It does not mention differences between
>> POSIXct and POSIXlt.
>>
>> Moreover, using diff() with POSIXlt has provided (wrong)
>> numbers... and not an error. This may be difficult to
>> detect sometimes along programme lines. Must one keep in
>> mind that diff() is reliably applicable only on POSIXct?
>> In this case, should not it bve mentionned in the
>> documentation?
>>
>> All the best,
>>
>> Patrick
>>
>>
>>
>>
>>
>>
>>
>> jim holtman a écrit : > Try converting to POSIXct:
>> >
>> > > str(dts) > 'POSIXlt', format: chr [1:10] "2003-04-15"
>> "2003-07-15" "2003-10-15" > "2004-04-15" "2004-07-15"
>> "2004-10-15" "2005-04-15" ... > > dts > [1] "2003-04-15"
>> "2003-07-15" "2003-10-15" "2004-04-15" "2004-07-15" >
>> "2004-10-15" "2005-04-15" "2005-07-15" > [9] "2005-10-15"
>> "2006-04-15" > > dts <- as.POSIXct(dts) > > dts > [1]
>> "2003-04-15 EDT" "2003-07-15 EDT" "2003-10-15 EDT"
>> "2004-04-15 > EDT" "2004-07-15 EDT" "2004-10-15 EDT" >
>> [7] "2005-04-15 EDT" "2005-07-15 EDT" "2005-10-15 EDT"
>> "2006-04-15 EDT" > > diff(dts) > Time differences of 91,
>> 92, 183, 91, 92, 182, 91, 92, 182 days
>> > >
>> >
>> >
>> >
>> > On 7/23/06, *Patrick Giraudoux*
>> <patrick.giraudoux@univ-fcomte.fr >
>> <mailto:patrick.giraudoux@univ-fcomte.fr>> wrote:
>> >
>> > Dear Listers,
>> >
>> > I have encountered a strange problem using diff() and
>> POSIXt:
>> >
>> >
>> dts<-c("15/4/2003","15/7/2003","15/10/2003","15/04/2004","15/07/2004","15/10/2004","15/4/2005","15/07/2005","15/10/2005","15/4/2006")
>> >
>> > dts <- strptime(dts, "%d/%m/%Y") > class(dts)
>> >
>> > [1] "POSIXt" "POSIXlt"
>> >
>> > diff(dts)
>> >
>> > Time differences of 7862400, 7948800, 15811200,
>> 7862400, 7948800, > 15724800, 7862400, 7948800, 0 secs
>> >
>> > In this case the result is not the one expected:
>> expressed in seconds > and not in days, and the
>> difference between the two last dates is > not 0.
>> >
>> > Now, if one use a vector of 9 dates only (whatever the
>> date removed), > things come well:
>> >
>> > diff(dts[-1])
>> >
>> > Time differences of 92, 183, 91, 92, 182, 91, 92, 182
>> days
>> >
>> > Also if one contrains dts to POSIXct
>> >
>> >
>> dts<-c("15/4/2003","15/7/2003","15/10/2003","15/04/2004","15/07/2004","15/10/2004","15/4/2005","15/07/2005","15/10/2005","15/4/2006")
>> >
>> > dts <- as.POSIXct(strptime(dts, "%d/%m/%Y")) >
>> diff(dts)
>> >
>> > Time differences of 91, 92, 183, 91, 92, 182, 91, 92,
>> 182 days
>> >
>> > Any rational in that?
>> >
>> > Patrick



R-help@stat.math.ethz.ch mailing list
https://stat.ethz.ch/mailman/listinfo/r-help PLEASE do read the posting guide http://www.R-project.org/posting-guide.html and provide commented, minimal, self-contained, reproducible code. Received on Mon Jul 24 20:40:01 2006

Archive maintained by Robert King, hosted by the discipline of statistics at the University of Newcastle, Australia.
Archive generated by hypermail 2.1.8, at Mon 24 Jul 2006 - 22:19:57 EST.

Mailing list information is available at https://stat.ethz.ch/mailman/listinfo/r-help. Please read the posting guide before posting to the list.