R 递归地从列表列表中提取元素
我有以下类型的嵌套列表: 我拥有的R 递归地从列表列表中提取元素,r,list,R,List,我有以下类型的嵌套列表: 我拥有的 mylist <- list( "A", list( "B1", list( "C_B1", "w" ), "B2", list( "C_B2", "x" ), "B3", list( "C_B
mylist <- list(
"A",
list(
"B1",
list(
"C_B1",
"w"
),
"B2",
list(
"C_B2",
"x"
),
"B3",
list(
"C_B3_1",
list(
"D_B3_1",
"y"
),
"C_B3_2",
list(
"D_B3_2",
"z"
)
)
)
)
注意嵌套的程度并没有保证,只是有一个列表,每个列表的第一个元素是列表中的值(第二个元素)的名称。我依赖于问题陈述“这里列表的名称实际上存储为每个列表中的第一个元素。”并使用遵循此规则的更正示例
mylist <-
list( "A",
list("B1",
list("C_B1",
"w"),
list("B2",
list( "C_B2",
"x")),
list("B3",
list( "C_B3_1",
list( "D_B3_1",
"y"),
list("C_B3_2",
list("D_B3_2",
"z")
)
)
)
)
)
mylist有点难看,但可以工作:
library(magrittr)
stackUp = function(lst)
{
cond = lst %>% sapply(is.list) %>% any
if(!cond) return(setNames(list(lst[[2]]), lst[[1]]))
index = seq(1, length(lst), 2)
index %>%
lapply(function(u) stackUp(lst[[u+1]])) %>%
setNames(sapply(index, function(u) lst[[u]]))
}
> stackUp(mylist)
#$A
#$A$B1
#$A$B1$C_B1
#[1] "w"
#$A$B2
#$A$B2$C_B2
#[1] "x"
#$A$B3
#$A$B3$C_B3_1
#$A$B3$C_B3_1$D_B3_1
#[1] "y"
#$A$B3$C_B3_2
#$A$B3$C_B3_2$D_B3_2
#[1] "z"
你的意图不清楚。除了在名称(当前的\u列表\u元素)
上递归之外,您还需要什么吗?@CarlWitthoft我试图用所需的输出来说明我想要的是什么,但我不确定如何解释它。我不认为names
有什么帮助,因为名称实际上是作为列表和每个嵌套子列表中的第一个元素存储的。您首先是如何在这个结构中获取数据的?嗯。。。您在双锐器(:-)后列出的内容不清楚。您如何知道何时已深入到实际数据(示例中的x、y、z)?如果你可以解释的话,那么一些黑客使用assign
或臭名昭著的eval(parse(paste0(names)(df[[1]])[1],@Dason:这是NLP包中的一棵树。这不太正确。请注意,它并不总是一个两元素列表。它有模式列表(name1,out1,name2,out2,name3,out3)。OP声明“在这里,列表的名称实际上存储为每个列表中的第一个元素。”我依靠的是一个示例(如上所述)这实际上符合这个说法。是的,他的示例数据和他在问题中所说的并不完全匹配。@Dason如果您能更清楚地说明,请进行编辑。在您的示例中,第一个嵌套列表有6个元素;奇数元素是名称,偶数元素是列表。这与该说法不匹配”这里列表的名称实际上存储为每个列表中的第一个元素。”因为名称“B1”、“B2”和“B3”不适合此模式。
firstEltAsName <- function(x){
# if x is not a list, return x
if(!inherits(x,'list'))
return(x)
# recurse on everythin but the first element
out <- lapply(x[-1],firstEltAsName)
# take the names from the first element of the remaining elements.
names(out) <- sapply(x[-1],`[`,1)
# use the first element as the name
return(out)
}
firstEltAsName( mylist)
OddEltsAsNames <- function(x){
stopifnot(length(x)%%2 == 0)
# recurse on the even elements
out <- lapply(x[which(seq_along(x)%%2 == 0)],firstEltAsName)
# take the names from the even elements
names(out) <- unlist( x[which(seq_along(x)%%2 == 1)] )
return(out)
}
OddEltsAsNames( mylist)
library(magrittr)
stackUp = function(lst)
{
cond = lst %>% sapply(is.list) %>% any
if(!cond) return(setNames(list(lst[[2]]), lst[[1]]))
index = seq(1, length(lst), 2)
index %>%
lapply(function(u) stackUp(lst[[u+1]])) %>%
setNames(sapply(index, function(u) lst[[u]]))
}
> stackUp(mylist)
#$A
#$A$B1
#$A$B1$C_B1
#[1] "w"
#$A$B2
#$A$B2$C_B2
#[1] "x"
#$A$B3
#$A$B3$C_B3_1
#$A$B3$C_B3_1$D_B3_1
#[1] "y"
#$A$B3$C_B3_2
#$A$B3$C_B3_2$D_B3_2
#[1] "z"