Lapply于数组列表



我有一个列表,其中包含多个数组列表。目标是计算第三维中每个数组的平均值。

因此,当数组的维数为c(54,71,360)时,结果的平均值应该是列表中每个成员的维数为c(54,71)的矩阵。

下面是一些重现样本数据的代码:

######################### create sample data ###########################
# create empty list
list1 <- list()
# fill the list with arrays
for (i in 1:10) {
list1[[i]] <- array(sample(1:100, 600, replace=T), dim= c(54,71,360))
}
# create the big list
big_list <- list()
for (i in 1:8) {
big_list[[paste0("list", i)]] <- list1
}

我可以使用for循环来实现它:

######################## way to do it with for loop ####################
for (i in 1:length(big_list)) {
for (j in 1:length(list1)) {
big_list[[i]][[j]] <- apply(big_list[[i]][[j]], 1:2, mean, na.rm= T)
}
}

我相信有一个更优雅的方式使用lapply嵌套的方式或一些东西,导致相同的结果只使用一行或两行。我一直在努力寻找一种方法将lapply命令与apply/sapply/etc.结合在一起,以便正确地接近单个列表中的数组。我想lapply是需要的,因为我需要列表的大列表作为结果。

有人知道怎么做吗?

可以,但是您将需要匿名函数的概念。实际上,您在lapply中间声明了自定义函数。这使您可以自由地在lapply中使用索引。

result = lapply(big_list, function(x) {
lapply(x, function(y) {
apply(y, 1:2, mean, na.rm= T)
}
)
}
)

艰难,我必须说,在这一点上,应用程序对代码的清晰度造成的伤害大于帮助。所以,我实际上会坚持使用for

如果可以删除嵌套的列表结构并重新创建它,那么使用lapply创建代码可能会更容易。但那是不可能的,因为你说过你必须保留它。

我认为你可以使用purrr和嵌套的map()s,它们类似于lapply,但具有更清晰的语法

library(purrr)
map(1:8, ~map(1:10, ~ array(sample(1:100, 600, replace=T), dim= c(54,71,360))))

如果你愿意,你可以继续使用lapply的基本R语法匿名函数以类似的方式:

lapply(1:8, (x) lapply(1:10, (y) array(sample(1:100, 600, replace=T), dim= c(54,71,360))))

最新更新