[R] name returned by lapply

Antje niederlein-rstat at yahoo.de
Fri Jul 18 14:55:23 CEST 2008


Thanks a lot for your help!

I know that I cannot directly access the list created, I just was not sure if 
there is any "format" of the return value which could provide additionally a 
name for the returned list.
I tried to return the values as list with the appropriate name but then I end 
up with a list entry as list entry...

Okay, then I'll solve it with a loop and thanks for the hint with the article

Ciao,
Antje





Gavin Simpson schrieb:
> On Fri, 2008-07-18 at 14:19 +0200, Antje wrote:
>> Hi Gavin,
>>
>> thanks a lot for your answer.
>> Maybe I did not explain very well what I want to do and probably chose a bad 
>> example. I don't mind spaces or names starting with a number. I could even name it:
>>
>> "Hugo1", "Hugo2", ...
>>
>> My biggest problem is, that not only the values are calculated/estimated within 
>> my function but also the names (Yes, in reality my funtion is more complicated).
>> Maybe it's easier to explain like this. the parameter x can be a coordinate 
>> position of mountains on earth. Within the funtion the height of the mountain 
>> is estimated and it's name.
>> In the end, I'd like to get a list, where the entry is named like the mountain 
>> and it contains its height (or other measurements...)
>>
>>
>>> ## now that we have a list, we change the names to what you want
>>> names(ret) <- paste(1:10, "info_within_function")
>> so this would not work, because I don't have the information anymore about the 
>> naming...
> 
> OK, so you can't do what you want to do in the manner you tried, via
> lapply as you don't have control of how the list is produced once the
> loop over 1:10 has been performed. At the stage that 'test' is being
> applied, all it knows about is 'x' and it doesn;t have access to the
> list being built up by lapply().
> 
> The *apply family of functions help us to *not* write out formal loops
> in R, but here this is causing you a problem. So we can specify an
> explicit loop and fill in information as and when we want from within
> the loop
> 
> ## create list to hold results
> n <- 10
> ret <- vector(mode = "list", length = n)
> ## initialise loop
> for(i in seq_len(n)) {
>     ## do whatever you need to do here, but this line just
>     ## replicates what 'test' did earlier
>     ret[[i]] <- c(1,2,3,4,5)
>     ## now add the name in
>     names(ret)[i] <- paste("Mountain", i, sep = "")
> }
> ret
> 
> Alternatively, collect a vector of names during the loop and then once
> the loop is finished do a single call to names(ret) to replace all the
> names at once:
> 
> n <- 10
> ret <- vector(mode = "list", length = n)
> ## new vector to hold vector of names
> name.vec <- character(n)
> for(i in seq_len(n)) {
>     ret[[i]] <- c(1,2,3,4,5)
>     ## now we just fill in this vector as we go
>     name.vec[i] <- paste("Mountain", i, sep = "")
> }
> ## now replace all the names at once
> names(ret) <- name.vec
> ret
> 
> This latter version is likely to more efficient if n is big so you don't
> incur the overhead of the repeated calls to names()
> 
> The moral of the story is to not jump to using *apply all the time to
> avoid loops. Loops in R are just fine, so use the tool that helps you do
> the job most efficiently *and* most transparently.
> 
> Take a look at the R Help Desk article by Uwe Ligges and John Fox in the
> current issue of RNews:
> 
> http://www.r-project.org/doc/Rnews/Rnews_2008-1.pdf
> 
> Which goes into this in much more detail
> 
> HTH
> 
> G
>



More information about the R-help mailing list