理解列表行为

时间:2016-11-08 11:42:08

标签: r list dataframe nested-lists

我觉得我对data.frames以及它们是如何工作有很好的理解,但是列表的某些方面让我感到困惑。

以下是一些可重现的数据:

 list_a <- structure(list(`one` = structure(list(
     words = c("a", "b","c", "d", "e", "f")), .Names = "words", class = "data.frame", row.names = c(NA,-6L)), 
     `two` = structure(list(words = c("a","s","t","z")), .Names = "words", class = "data.frame", row.names = c(NA, -4L))),
     .Names = c("one", "two"))

这给了我们:

list_a
$one
  words
1     a
2     b
3     c
4     d
5     e
6     f

$two
  words
1     a
2     s
3     t
4     z

现在我想遍历列表以返回data.frames中的一些结果。

list <- list()

for(i in list_a){list <- append(list, list_a$i$words)}

这不会在列表中产生任何结果。也没有:

for(i in list_a){list <- append(list, list_a[[i]]$words)}
Error in list_a[[i]] : invalid subscript type 'list'

我想也许我的第一个循环没有工作的原因是我使用list_a$i$words而没有将i定义为正确的名称。所以我试过了:

for(i in names(list_a)){list <- append(list, list_a$i$words)}

这仍然给我一个长度为0的列表。

所以我不明白为什么我尝试的尝试没有给出我期望的结果,我不知道为什么使用下标给了我一个错误,最后我想出了正确的语法:

for(i in list_a){list2 <- append(list2, i$words)}

但是我不知道为什么在使用names方法时这没有用呢?

1 个答案:

答案 0 :(得分:0)

R中for表达式的参数包括:

  • LHS,一个将采用RHS的每个值的迭代器
  • in,语言关键字
  • RHS,一个向量,其长度定义将发生的迭代次数。

当您设置第一个循环时,RHS是类型为&#34; list&#34;的长度为2的向量。在LHS上,您有i这是一列数据框。然后,您要求$提取&#34; i&#34;来自list_a,评估为NULL。在你的第二个循环中,RHS是&#34;字符&#34;的长度为2的向量。发生了同样的事情。

$不评估其索引。请改用[[,您将在第二个循环中得到您期望的答案。

# initialize
list <- list()
# loop
for (i in names(list_a)) {
    list <- append(list, list_a[[i]]$words)
}
list
# [[1]]
# [1] "a"
#
# [[2]]
# [1] "b"
# ...

如Roland所述,R中的追加非常昂贵,因为每次迭代都会创建一个新的对象副本。以下是尝试的另一种选择:

# create a data frame using all of list_a, 
# coerce to character vector
# then coerce to list
as.list(unname(unlist(do.call(what = "rbind", args = list_a))))

请注意&#34; data.frame&#34;对象只是&#34; list&#34;具有&#34; data.frame&#34;的对象应用了class属性。因此,在使用带有未评估名称的data.frames和$以及列表时,您将看到相同的行为。试试这个:

# print mtcars data.frame
mtcars
# set class attribute to NULL
class(mtcars) <- NULL
# mtcars is just a list now :-)
mtcars

编辑:$[[是运算符,这意味着它们是可以以特殊方式使用的函数。您可以像普通函数一样使用它们,将它们的参数传递给圆括号。

# $ is a function
`$`(list_a, "one")
#   words
# 1     a
# 2     b
# ...

这些功能的行为是不同的。 [[期望它解释的对象。 $需要一个它试图找到的元素名称。

i <- "one"
# $ is a function, but there is no element "i"
`$`(list_a, i)
# NULL
# [[ is a function, and an element "one" is present
`[[`(list_a, i)
#   words
# 1     a
# 2     b
# ...