R: Named lists and description lists - r

R has two classes not so commonly used: "Dlist" and "namedList".
As regard the first, it is mentioned with respect to Sys.getenv(), which returns a result of class "Dlist" if its argument is missing, for nice printing. There is in fact a print.Dlist method for the class. There is also an apparently related formatDL function to format description lists. However I do not know how to create an object of class "Dlist".
As regards "namedList", it is defined by the manual:
the alternative to "list" that preserves the names attribute
In this case I am unable to create an object of this type and I have not found any instance where it is used.
How do you create a "Dlist" or a "namedList"?
Can you provide an example where the "namedList" is more convenient of an ordinary named list? (intended as a list L, where names(L) is not NULL)

A Dlist is an informal class defined in R's Base package that exists for the sole purpose of pretty-printing a named character vector. It's not a list at all, but a type of character vector:
a <- Sys.getenv()
class(a)
# [1] "Dlist"
typeof(a)
# [1] "character"
You can make one just by writing Dlist to a named character vector's class attribute:
hello_world <- c(Hello = "World", Hi = "Earth", Greetings = "planet");
class(hello_world) <- "Dlist"
hello_world
# Hello World
# Hi Earth
# Greetings planet
You can select formatting options with formatDL:
cat(formatDL(hello_world, style = "list", width = 20), sep = "\n")
# Hello: World
# Hi: Earth
# Greetings: planet
The Dlist is only used in base R for printing environmental variables to the console. Unless you wanted to have a named character vector printed this way, you don't need a Dlist.
On the other hand, a namedList is a formal S4 object as defined in the methods package (also preloaded in R). It inherits its attributes from list and defines a single method - its own version of the generic S4 show.
You might use it as a base class from which to make new S4 classes that inherit the properties of a named list (i.e. a normal list with a names attribute), although it's not clear why a user advanced enough to create S4 classes wouldn't just do that themselves. It's defined here.
You can create a namedList with new:
n <- new("namedList", list(a=1, b=2))
n
# An object of class “namedList”
# $`a`
# [1] 1
#
# $b
# [1] 2
isS4(n)
# [1] TRUE

Related

Change name of column vector in R [duplicate]

so we know that R have list() variable, and also know that R has function call names() to give names for variable. For example :
a=30
names(a)="number"
a
# number
# 30
But now, I want to give a list variable a name, like this :
b=list()
names(b)="number"
and it returns error message like this :
Error in names(b) = "number" :
'names' attribute [1] must be the same length as the vector [0]
What I have suppose to do? I do this because I need many list variables. Or, do you have another way so I can make many list variables without playing with its name?
Since #akrun doesn't need any more points, here is an example showing how you can assign names to a list:
lst <- list(a="one", b="two", c=c(1:3))
names(lst)
[1] "a" "b" "c"
names(lst) <- c("x", "y", "z")
> lst
$x
[1] "one"
$y
[1] "two"
$z
[1] 1 2 3
It seems as though you are interested in labeling the object itself rather than the elements in it. The key is that the names attribute for a list object is necessarily assigned to its elements. One option, since you said you have many list objects, is to store the lists in a big list and then you can assign names to the big list, and the elements within the list-objects can be named too.
allLists <- list('number' = list())
> allLists
$number
list()
Another option, you can make use of the label feature in the Hmisc package. It modifies most common objects in R to have a subclass "labelled" and so whenever you print the list it shows the label. It is good for documentation and organizing the workspace a bit better, but caveat it's very easy to accidentally cast labelled objects to a non-labelled class and to confuse methods that don't think to search for more than one class.
library(Hmisc)
p <- list()
label(p) <- 'number'
> p
number
list()
Another option is to make the "name" of your list object an actual element of the list. You'll see in a lot of complex R data structures, this is the preferred way of storing labels, titles, or names when such a need arises and isn't met by the base R data structure.
b <- list('name' = 'number')
The last possibility is that you need a placeholder to store the "names" attribute of the elements you haven't yet populated the list with. If the elements are of known length and of known type, you can allocate such a vector using e.g. numeric(1) a sort-of "primed" vector which can be named. If you don't know the data structure of your output, I would not use this approach since it can be a real memory hog to "build" data structures in R.
Other possibilities are
as.list(a)
# $`number`
# [1] 30
# or
setNames(list(unname(a)),'number')
# $`number`
# [1] 30
# or named list with named vector
setNames(list(a), 'number')
# $`number`
# number
# 30

assign names of elements in a list in a for loop [duplicate]

so we know that R have list() variable, and also know that R has function call names() to give names for variable. For example :
a=30
names(a)="number"
a
# number
# 30
But now, I want to give a list variable a name, like this :
b=list()
names(b)="number"
and it returns error message like this :
Error in names(b) = "number" :
'names' attribute [1] must be the same length as the vector [0]
What I have suppose to do? I do this because I need many list variables. Or, do you have another way so I can make many list variables without playing with its name?
Since #akrun doesn't need any more points, here is an example showing how you can assign names to a list:
lst <- list(a="one", b="two", c=c(1:3))
names(lst)
[1] "a" "b" "c"
names(lst) <- c("x", "y", "z")
> lst
$x
[1] "one"
$y
[1] "two"
$z
[1] 1 2 3
It seems as though you are interested in labeling the object itself rather than the elements in it. The key is that the names attribute for a list object is necessarily assigned to its elements. One option, since you said you have many list objects, is to store the lists in a big list and then you can assign names to the big list, and the elements within the list-objects can be named too.
allLists <- list('number' = list())
> allLists
$number
list()
Another option, you can make use of the label feature in the Hmisc package. It modifies most common objects in R to have a subclass "labelled" and so whenever you print the list it shows the label. It is good for documentation and organizing the workspace a bit better, but caveat it's very easy to accidentally cast labelled objects to a non-labelled class and to confuse methods that don't think to search for more than one class.
library(Hmisc)
p <- list()
label(p) <- 'number'
> p
number
list()
Another option is to make the "name" of your list object an actual element of the list. You'll see in a lot of complex R data structures, this is the preferred way of storing labels, titles, or names when such a need arises and isn't met by the base R data structure.
b <- list('name' = 'number')
The last possibility is that you need a placeholder to store the "names" attribute of the elements you haven't yet populated the list with. If the elements are of known length and of known type, you can allocate such a vector using e.g. numeric(1) a sort-of "primed" vector which can be named. If you don't know the data structure of your output, I would not use this approach since it can be a real memory hog to "build" data structures in R.
Other possibilities are
as.list(a)
# $`number`
# [1] 30
# or
setNames(list(unname(a)),'number')
# $`number`
# [1] 30
# or named list with named vector
setNames(list(a), 'number')
# $`number`
# number
# 30

An imported package is an object of what kind? [duplicate]

I am (probably) NOT referring to the "all other variables" meaning like var1~. here.
I was pointed to plyr once again and looked into mlplyand wondered why parameters are defined with leading dot like this:
function (.data, .fun = NULL, ..., .expand = TRUE, .progress = "none",
.parallel = FALSE)
{
if (is.matrix(.data) & !is.list(.data))
.data <- .matrix_to_df(.data)
f <- splat(.fun)
alply(.data = .data, .margins = 1, .fun = f, ..., .expand = .expand,
.progress = .progress, .parallel = .parallel)
}
<environment: namespace:plyr>
What's the use of that? Is it just personal preference, naming convention or more? Often R is so functional that I miss a trick that's long been done before.
A dot in function name can mean any of the following:
nothing at all
a separator between method and class in S3 methods
to hide the function name
Possible meanings
1. Nothing at all
The dot in data.frame doesn't separate data from frame, other than visually.
2. Separation of methods and classes in S3 methods
plot is one example of a generic S3 method. Thus plot.lm and plot.glm are the underlying function definitions that are used when calling plot(lm(...)) or plot(glm(...))
3. To hide internal functions
When writing packages, it is sometimes useful to use leading dots in function names because these functions are somewhat hidden from general view. Functions that are meant to be purely internal to a package sometimes use this.
In this context, "somewhat hidden" simply means that the variable (or function) won't normally show up when you list object with ls(). To force ls to show these variables, use ls(all.names=TRUE). By using a dot as first letter of a variable, you change the scope of the variable itself. For example:
x <- 3
.x <- 4
ls()
[1] "x"
ls(all.names=TRUE)
[1] ".x" "x"
x
[1] 3
.x
[1] 4
4. Other possible reasons
In Hadley's plyr package, he uses the convention to use leading dots in function names. This as a mechanism to try and ensure that when resolving variable names, the values resolve to the user variables rather than internal function variables.
Complications
This mishmash of different uses can lead to very confusing situations, because these different uses can all get mixed up in the same function name.
For example, to convert a data.frame to a list you use as.list(..)
as.list(iris)
In this case as.list is a S3 generic method, and you are passing a data.frame to it. Thus the S3 function is called as.list.data.frame:
> as.list.data.frame
function (x, ...)
{
x <- unclass(x)
attr(x, "row.names") <- NULL
x
}
<environment: namespace:base>
And for something truly spectacular, load the data.table package and look at the function as.data.table.data.frame:
> library(data.table)
> methods(as.data.table)
[1] as.data.table.data.frame* as.data.table.data.table* as.data.table.matrix*
Non-visible functions are asterisked
> data.table:::as.data.table.data.frame
function (x, keep.rownames = FALSE)
{
if (keep.rownames)
return(data.table(rn = rownames(x), x, keep.rownames = FALSE))
attr(x, "row.names") = .set_row_names(nrow(x))
class(x) = c("data.table", "data.frame")
x
}
<environment: namespace:data.table>
At the start of a name it works like the UNIX filename convention to keep objects hidden by default.
ls()
character(0)
.a <- 1
ls()
character(0)
ls(all.names = TRUE)
[1] ".a"
It can be just a token with no special meaning, it's not doing anything more than any other allowed token.
my.var <- 1
my_var <- 1
myVar <- 1
It's used for S3 method dispatch. So, if I define simple class "myClass" and create objects with that class attribute, then generic functions such as print() will automatically dispatch to my specific print method.
myvar <- 1
print(myvar)
class(myvar) <- c("myClass", class(myvar))
print.myClass <- function(x, ...) {
print(paste("a special message for myClass objects, this one has length", length(x)))
return(invisible(NULL))
}
print(myvar)
There is an ambiguity in the syntax for S3, since you cannot tell from a function's name whether it is an S3 method or just a dot in the name. But, it's a very simple mechanism that is very powerful.
There's a lot more to each of these three aspects, and you should not take my examples as good practice, but they are the basic differences.
If a user defines a function .doSomething and is lazy to specify all the roxygen documentation for parameters, it will not generate errors for compiling the package

coerce class data type in R with as

I understand that in R you have some base data types (vector, matrix, list, data.frame) and then in the R packages you have some advanced types called S3-class or S4-class (ppp,owin, spatialPointsDataFrame and many others. Some of the functions in R packages only work with arguments of special type.
I need explanation about converting between different classes and data types in R:
Sometimes I can use a code like:
m = c(1, 2, 3, 4)
df = as.data.frame(m)
But in other cases I must use a code like:
shp = readShapeSpatial("polygons.shp")
win = as(shp,"owin")
How do I know which syntax of the as to use for which object?
Or is the syntax: as.foo(originalObject) always equivalent to as(originalObject, "foo") (here foo stands for the class that I want to convert my object to so that I can use in a function that requires its argument to be a foo class)
Let's say I use a package in R with a class foo. And I have a variable v that belongs to class bar (in other words, class(v) is bar). How do I know if the function as(v,"foo") will work?
as.data.frame is an S3 method that you can check for foo using :
getS3method('as.data.frame','foo')
But I think you are looking for ( as it is commented)
showMethods(coerce)
This will give you a list of predefined coerce funsctions.
To define you coerce function , one option (there are many options like setIS , coerce<- and implicit coercion through inheritance) is to use setAs. Here an example:
track <- setClass("track",
slots = c(x="numeric", y="numeric"))
setAs("track", "numeric", function(from) from#y)
t1 <- new("track", x=1:20, y=(1:20)^2)
as(t1, "numeric")
Now if I check using :
showMethods(coerce)
You get an entry with :
from="track", to="numeric"
For better explanation you should read help("as") but the subject is not very simple.
EDIT To show only the entries with track you can do this for example:
cat(grep('track',showMethods(coerce,printTo=FALSE),value=TRUE))
from="track", to="numeric"

R sub-setting the list of objects in the global environment by class

I would like to be able to subset the list of objects in my Global Environment by class.
i.e. from the list created by running
ls()
I would like to be able to make a shorter list that only has the names of the objects that belong to specific class e.g. xts or POSIXlt
Thanks in advance
This is a slight twist to the above which uses inherits to inspect the object:
objs = mget(ls(envir=.GlobalEnv), envir=.GlobalEnv)
names(Filter(function(i) inherits(i, "lm"), objs))
The function(i) inherits(i, "lm") can be adjusted as you want.
You could retrieve ls() and check the class of everything. It may not be particularly efficient though, as it does the filtering after ls() and not within.
# populate global environment with some vars.
rm(list=ls())
a <- 1
b <- 2
c <- 'foo'
d <- 'asdf'
lst <- ls()
# return everything 'numeric':
lst[sapply(lst,function(var) any(class(get(var))=='numeric'))]
# 'a' 'b'
The get(var) gets the variable corresponding to the string in var, so if var is "a" then get(var) retrieves 1 (being the value of variable a).
As #VincentZoonekynd notes below - it is possible for objects to have multiple classes. Soo class(some_xts_object) is c("xts","zoo") -- the above method will return some_xts_object if you search for xts objects, but also if you search for zoo objects.

Resources