Welcome to OGeek Q&A Community for programmer and developer-Open, Learning and Share
Welcome To Ask or Share your Answers For Others

Categories

0 votes
551 views
in Technique[技术] by (71.8m points)

r - Flatten nested list into 1-deep list

I am looking for an efficient solution to (recursively) flatten a nested list (of arbitrary depth) into non-nested, 1 deep list. The list elements are not homogeneous, therefore they should not be unlisted into a vector (that would coerce all values to a single type). The best solution so far is:

flatlist <- function(mylist){
    lapply(rapply(mylist, enquote, how="unlist"), eval)
}

This does almost what I want:

> flatlist(list(foo=TRUE, bar=456, pets=list(cat="meeuw", dog="woof")))
$foo
[1] TRUE

$bar
[1] 456

$pets.cat
[1] "meeuw"

$pets.dog
[1] "woof"

However, a problem is that rapply is dropping NULL values, which is undesired:

> flatlist(list(foo=123, bar=NULL))
$foo
[1] 123

I would like that NULL elements appear in the output, either as NULL or as NA. Also the double loop with enquote and then eval makes things a bit slow. This function is used extensively in my code. Is there a way to do it all in one run?

See Question&Answers more detail:os

与恶龙缠斗过久,自身亦成为恶龙;凝视深渊过久,深渊将回以凝视…
Welcome To Ask or Share your Answers For Others

1 Reply

0 votes
by (71.8m points)

Replace the rapply part by your own recursion so NULLs are not getting any special treatment:

renquote <- function(l) if (is.list(l)) lapply(l, renquote) else enquote(l)

lapply(unlist(renquote(ml)), eval)

与恶龙缠斗过久,自身亦成为恶龙;凝视深渊过久,深渊将回以凝视…
OGeek|极客中国-欢迎来到极客的世界,一个免费开放的程序员编程交流平台!开放,进步,分享!让技术改变生活,让极客改变未来! Welcome to OGeek Q&A Community for programmer and developer-Open, Learning and Share
Click Here to Ask a Question

...