From jmc at research.bell-labs.com  Thu May 22 12:37:18 2003
From: jmc at research.bell-labs.com (John Chambers)
Date: Thu May 22 17:39:27 2003
Subject: [Rd] Re: as(df, "list") does not propagate names
References: <6r1xyrenp5.fsf@r-project.org>
Message-ID: <3ECCEEAE.5AEEBF94@research.bell-labs.com>

(I enlarged this mail from r-core to r-devel since it's an interesting
question for general discussion.)

Douglas Bates wrote:
> 
> In a recent r-patched I notice that when df is a data.frame
> as(df, "list") does not propagate the names whereas as.list(df) does.
> Is this intentional?

Well, it's explicit anyway.  The as() function uses method dispatch for
coerce() to find methods.

R> selectMethod("coerce", c("data.frame", "list"))
function (from, to, strict = TRUE) 
{
    value <- as.list(from)
    if (strict) 
        attributes(value) <- NULL
    value
}

(This is actually the method for c("ANY","list").)

The strict=FALSE option is analogous to what would happen in method
dispatch if "list" were a superclass of "data.frame" (which it isn't
since "data.frame" is an S3 class.)

Two points about as.list:

1- Generally, it leaves all attributes alone.

2- There is an S3 method, as.list.data.frame, that deletes the "class"
and "row.names" attributes, but leaves the names.

So putting these all together:  Given 1, I think the general behavior
needs to stay the same (in fact, one might argue that even with
strict=FALSE, the class attribute should be reset).

But it seems reasonable to promote the as.list.data.frame method to an
S4 method for coerce().  

This prompts a general question:  do we want to promote certain S3
methods?  (It happens that as.list.data.frame is the only non-default
method for as.list, but there are 31 apparent non-default as.* methods. 
Promoting them would encourage use of as() for consistent programming.)

John

PS: The comparative behavior of as() and as.list() is illustrated below:

R> attributes(as.list(women))
$names
[1] "height" "weight"

R> attributes(as(women, "list"))
NULL
R> attributes(as(women, "list", strict=F))
$names
[1] "height" "weight"

R> x <- list(a=1,b=2)
R> class(x) <- "something"
R> attr(x, "foo") <- pi
R> as.list(x)
$a
[1] 1

$b
[1] 2

attr(,"class")
[1] "something"
attr(,"foo")
[1] 3.141593
R> as(x, "list")
[[1]]
[1] 1

[[2]]
[1] 2

and as(x, "list", FALSE) is the same result as as.list(x).




> 
> > data(women)
> > class(women)
> [1] "data.frame"
> > as.list(women)
> $height
>  [1] 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72
> 
> $weight
>  [1] 115 117 120 123 126 129 132 135 139 142 146 150 154 159 164
> 
> > as(women, "list")
> [[1]]
>  [1] 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72
> 
> [[2]]
>  [1] 115 117 120 123 126 129 132 135 139 142 146 150 154 159 164
> 
> _______________________________________________


-- 
John M. Chambers                  jmc@bell-labs.com
Bell Labs, Lucent Technologies    office: (908)582-2681
700 Mountain Avenue, Room 2C-282  fax:    (908)582-3340
Murray Hill, NJ  07974            web: http://www.cs.bell-labs.com/~jmc


[Rd] Re: as(df, "list") does not propagate names
John Chambers