从 R 中的 S4 class 列表中提取和合并数据帧
Extracting and merging dataframes from an S4 class list in R
我有一个 S4 class 列表(称为 vi2)。这是它的第一部分:
- @variables: chr [1:7]
- @vImplist:400 人名单
- $1: 正式 class '.vImp' 有 2 个插槽
- @变量:chr [1:7]
- @vImp:'data.frame':7 bs。 3个变量:
- $variables:因子 w/ 7 水平
- $Ctest: num [1:7]
- $Atest: num [1:7]
- $2: 正式 class '.vImp' 有 2 个插槽
- @变量:chr [1:7]
- @vImp:'data.frame':7 bs。 3个变量:
- $variables:因子 w/ 7 水平
- $Ctest: num [1:7]
- $Atest: num [1:7]
总共有 400 classes 的 '.vImp' 都是相同的格式。我想要做的是提取 '@vImp: 数据。 frame' 为每个 class 并将它们合并到一个新的数据帧中。我可以使用以下行单独执行此操作:
vic = as.data.frame(vi2@vImplist$'1'@vImp)
这会生成 data.frame 以及 class 的正确信息。但是,当我尝试一次对所有 400 classes 执行此操作时,它失败了。
vic = as.data.frame(vi2@vImplist$'1:400'@vImp)
错误。data.frame(vi2@vImplist$'1:400'@vImp) :
试图从没有插槽的基本 class ("NULL") 的对象中获取插槽 "vImp"。
我也试过用循环来完成任务。但是,这也因同样的错误而失败:
for (i in seq(from = 1, to = 1, by = 1)) {
vic = as.data.frame(vi2@vImplist$'[i]'@vImp)
output <- rbind(newdf,vic)
}
有人对问题可能有什么建议吗?
根据给定的信息,vImplist
是一个包含 400 个条目的列表,因此您想访问每个条目。条目的名称为 '1'
、...、'400'
。因此,您的代码 vic = as.data.frame(vi2@vImplist$'1'@vImp)
有效。您通过名称引用列表条目('1'
是一个字符)。当您使用 '1:400'
或 '[i]'
时,由于 ''
,这也会被解释为名称。因为这些 data.frames 不存在,所以返回 NULL
,它试图从中检索插槽 "vImp"。这解释了您的错误消息。
您需要遍历列表的所有条目。最简单的方法是使用 lapply
执行此操作,它对列表的每个条目进行操作,您可以检索正确的插槽:
vic <- lapply(vi2@vImplist, function(x) {
as.data.frame(x@vImp)
})
vic
现在是 data.frames 的列表。如果将 rbind
与 do.call
一起使用,则可以直接使用 data.frames 的列表作为输入参数,因为 do.call
接受参数列表:
output <- do.call("rbind", vic)
编辑
正如@Rui Barradas 指出的那样,vImp
已经是一个 data.frame,因此您不需要 as.data.frame
。此外,您可以使用 slot
直接访问插槽,并将访问的插槽的名称用作函数的进一步参数:
vic <- lapply(vi2@vImplist, slot, 'vImp')
我有一个 S4 class 列表(称为 vi2)。这是它的第一部分:
- @variables: chr [1:7]
- @vImplist:400 人名单
- $1: 正式 class '.vImp' 有 2 个插槽
- @变量:chr [1:7]
- @vImp:'data.frame':7 bs。 3个变量:
- $variables:因子 w/ 7 水平
- $Ctest: num [1:7]
- $Atest: num [1:7]
- $variables:因子 w/ 7 水平
- $2: 正式 class '.vImp' 有 2 个插槽
- @变量:chr [1:7]
- @vImp:'data.frame':7 bs。 3个变量:
- $variables:因子 w/ 7 水平
- $Ctest: num [1:7]
- $Atest: num [1:7]
- $variables:因子 w/ 7 水平
- $1: 正式 class '.vImp' 有 2 个插槽
总共有 400 classes 的 '.vImp' 都是相同的格式。我想要做的是提取 '@vImp: 数据。 frame' 为每个 class 并将它们合并到一个新的数据帧中。我可以使用以下行单独执行此操作:
vic = as.data.frame(vi2@vImplist$'1'@vImp)
这会生成 data.frame 以及 class 的正确信息。但是,当我尝试一次对所有 400 classes 执行此操作时,它失败了。
vic = as.data.frame(vi2@vImplist$'1:400'@vImp)
错误。data.frame(vi2@vImplist$'1:400'@vImp) : 试图从没有插槽的基本 class ("NULL") 的对象中获取插槽 "vImp"。
我也试过用循环来完成任务。但是,这也因同样的错误而失败:
for (i in seq(from = 1, to = 1, by = 1)) {
vic = as.data.frame(vi2@vImplist$'[i]'@vImp)
output <- rbind(newdf,vic)
}
有人对问题可能有什么建议吗?
根据给定的信息,vImplist
是一个包含 400 个条目的列表,因此您想访问每个条目。条目的名称为 '1'
、...、'400'
。因此,您的代码 vic = as.data.frame(vi2@vImplist$'1'@vImp)
有效。您通过名称引用列表条目('1'
是一个字符)。当您使用 '1:400'
或 '[i]'
时,由于 ''
,这也会被解释为名称。因为这些 data.frames 不存在,所以返回 NULL
,它试图从中检索插槽 "vImp"。这解释了您的错误消息。
您需要遍历列表的所有条目。最简单的方法是使用 lapply
执行此操作,它对列表的每个条目进行操作,您可以检索正确的插槽:
vic <- lapply(vi2@vImplist, function(x) {
as.data.frame(x@vImp)
})
vic
现在是 data.frames 的列表。如果将 rbind
与 do.call
一起使用,则可以直接使用 data.frames 的列表作为输入参数,因为 do.call
接受参数列表:
output <- do.call("rbind", vic)
编辑
正如@Rui Barradas 指出的那样,vImp
已经是一个 data.frame,因此您不需要 as.data.frame
。此外,您可以使用 slot
直接访问插槽,并将访问的插槽的名称用作函数的进一步参数:
vic <- lapply(vi2@vImplist, slot, 'vImp')