Make an array by selecting data from two sub-lists in a big list

Viewed 33

I need to make a three dimensional array with data in a list A. I am not sure if I can use [] directly to select data from two sub-lists in a list. As an example, I want to make an array by A$aa$a and A$bb$a. Can I select them by A[[1:2]][1] and make the array by the codes below?

A <- list (aa = list(a = data.frame(matrix(1:10,10,15)),
                      b = data.frame(matrix(1:10,10,15))),
            bb = list(a = data.frame(matrix(1:10,10,15)),
                      b = data.frame(matrix(1:10,10,15))))

b <- lapply(A[[1:2]][1], as.matrix)
c <- c(b, recursive = TRUE)
d <- array(c, dim=c(10,15,2))
1 Answers

You could use abind from the abind library. I slightly changed your example data to be able to distinguish between a and b sub lists.

The method is similar to using rbind on multiple data frames, where we need do.call. We concatenate along=3 argument for abind to bnid along third dimension.

The first case where we want the a lists in each case is straightforward using lapply.

library(abind)
do.call(abind, c(lapply(A, `[[`, "a"), along=3))
# , , aa
# 
#      X1 X2 X3 X4 X5 X6 X7 X8 X9 X10 X11 X12 X13 X14 X15
# [1,]  1  1  1  1  1  1  1  1  1   1   1   1   1   1   1
# [2,]  2  2  2  2  2  2  2  2  2   2   2   2   2   2   2
# [3,]  3  3  3  3  3  3  3  3  3   3   3   3   3   3   3
# [4,]  4  4  4  4  4  4  4  4  4   4   4   4   4   4   4
# [5,]  5  5  5  5  5  5  5  5  5   5   5   5   5   5   5
# [6,]  6  6  6  6  6  6  6  6  6   6   6   6   6   6   6
# [7,]  7  7  7  7  7  7  7  7  7   7   7   7   7   7   7
# [8,]  8  8  8  8  8  8  8  8  8   8   8   8   8   8   8
# [9,]  9  9  9  9  9  9  9  9  9   9   9   9   9   9   9
# [10,] 10 10 10 10 10 10 10 10 10  10  10  10  10  10  10
# 
# , , bb
# 
#      X1 X2 X3 X4 X5 X6 X7 X8 X9 X10 X11 X12 X13 X14 X15
# [1,]  1  1  1  1  1  1  1  1  1   1   1   1   1   1   1
# [2,]  2  2  2  2  2  2  2  2  2   2   2   2   2   2   2
# [3,]  3  3  3  3  3  3  3  3  3   3   3   3   3   3   3
# [4,]  4  4  4  4  4  4  4  4  4   4   4   4   4   4   4
# [5,]  5  5  5  5  5  5  5  5  5   5   5   5   5   5   5
# [6,]  6  6  6  6  6  6  6  6  6   6   6   6   6   6   6
# [7,]  7  7  7  7  7  7  7  7  7   7   7   7   7   7   7
# [8,]  8  8  8  8  8  8  8  8  8   8   8   8   8   8   8
# [9,]  9  9  9  9  9  9  9  9  9   9   9   9   9   9   9
# [10,] 10 10 10 10 10 10 10 10 10  10  10  10  10  10  10

For slightly more nested calls, we use Map, which iterates continuously over the elements of multiple vectors in arguments.

do.call(abind, c(Map(function(x, y) `[[`(A[[x]], y),  c("aa", "bb"), c("a", "b")), along=3))
# , , aa
# 
#      X1 X2 X3 X4 X5 X6 X7 X8 X9 X10 X11 X12 X13 X14 X15
# [1,]  1  1  1  1  1  1  1  1  1   1   1   1   1   1   1
# [2,]  2  2  2  2  2  2  2  2  2   2   2   2   2   2   2
# [3,]  3  3  3  3  3  3  3  3  3   3   3   3   3   3   3
# [4,]  4  4  4  4  4  4  4  4  4   4   4   4   4   4   4
# [5,]  5  5  5  5  5  5  5  5  5   5   5   5   5   5   5
# [6,]  6  6  6  6  6  6  6  6  6   6   6   6   6   6   6
# [7,]  7  7  7  7  7  7  7  7  7   7   7   7   7   7   7
# [8,]  8  8  8  8  8  8  8  8  8   8   8   8   8   8   8
# [9,]  9  9  9  9  9  9  9  9  9   9   9   9   9   9   9
# [10,] 10 10 10 10 10 10 10 10 10  10  10  10  10  10  10
# 
# , , bb
# 
#      X1 X2 X3 X4 X5 X6 X7 X8 X9 X10 X11 X12 X13 X14 X15
# [1,]  2  2  2  2  2  2  2  2  2   2   2   2   2   2   2
# [2,]  3  3  3  3  3  3  3  3  3   3   3   3   3   3   3
# [3,]  4  4  4  4  4  4  4  4  4   4   4   4   4   4   4
# [4,]  5  5  5  5  5  5  5  5  5   5   5   5   5   5   5
# [5,]  6  6  6  6  6  6  6  6  6   6   6   6   6   6   6
# [6,]  7  7  7  7  7  7  7  7  7   7   7   7   7   7   7
# [7,]  8  8  8  8  8  8  8  8  8   8   8   8   8   8   8
# [8,]  9  9  9  9  9  9  9  9  9   9   9   9   9   9   9
# [9,] 10 10 10 10 10 10 10 10 10  10  10  10  10  10  10
# [10,] 11 11 11 11 11 11 11 11 11  11  11  11  11  11  11
    

Data:

A <- list(aa = list(a = structure(list(X1 = 1:10, X2 = 1:10, X3 = 1:10, 
    X4 = 1:10, X5 = 1:10, X6 = 1:10, X7 = 1:10, X8 = 1:10, X9 = 1:10, 
    X10 = 1:10, X11 = 1:10, X12 = 1:10, X13 = 1:10, X14 = 1:10, 
    X15 = 1:10), class = "data.frame", row.names = c(NA, -10L
)), b = structure(list(X1 = c(2, 3, 4, 5, 6, 7, 8, 9, 10, 11), 
    X2 = c(2, 3, 4, 5, 6, 7, 8, 9, 10, 11), X3 = c(2, 3, 4, 5, 
    6, 7, 8, 9, 10, 11), X4 = c(2, 3, 4, 5, 6, 7, 8, 9, 10, 11
    ), X5 = c(2, 3, 4, 5, 6, 7, 8, 9, 10, 11), X6 = c(2, 3, 4, 
    5, 6, 7, 8, 9, 10, 11), X7 = c(2, 3, 4, 5, 6, 7, 8, 9, 10, 
    11), X8 = c(2, 3, 4, 5, 6, 7, 8, 9, 10, 11), X9 = c(2, 3, 
    4, 5, 6, 7, 8, 9, 10, 11), X10 = c(2, 3, 4, 5, 6, 7, 8, 9, 
    10, 11), X11 = c(2, 3, 4, 5, 6, 7, 8, 9, 10, 11), X12 = c(2, 
    3, 4, 5, 6, 7, 8, 9, 10, 11), X13 = c(2, 3, 4, 5, 6, 7, 8, 
    9, 10, 11), X14 = c(2, 3, 4, 5, 6, 7, 8, 9, 10, 11), X15 = c(2, 
    3, 4, 5, 6, 7, 8, 9, 10, 11)), class = "data.frame", row.names = c(NA, 
-10L))), bb = list(a = structure(list(X1 = 1:10, X2 = 1:10, X3 = 1:10, 
    X4 = 1:10, X5 = 1:10, X6 = 1:10, X7 = 1:10, X8 = 1:10, X9 = 1:10, 
    X10 = 1:10, X11 = 1:10, X12 = 1:10, X13 = 1:10, X14 = 1:10, 
    X15 = 1:10), class = "data.frame", row.names = c(NA, -10L
)), b = structure(list(X1 = c(2, 3, 4, 5, 6, 7, 8, 9, 10, 11), 
    X2 = c(2, 3, 4, 5, 6, 7, 8, 9, 10, 11), X3 = c(2, 3, 4, 5, 
    6, 7, 8, 9, 10, 11), X4 = c(2, 3, 4, 5, 6, 7, 8, 9, 10, 11
    ), X5 = c(2, 3, 4, 5, 6, 7, 8, 9, 10, 11), X6 = c(2, 3, 4, 
    5, 6, 7, 8, 9, 10, 11), X7 = c(2, 3, 4, 5, 6, 7, 8, 9, 10, 
    11), X8 = c(2, 3, 4, 5, 6, 7, 8, 9, 10, 11), X9 = c(2, 3, 
    4, 5, 6, 7, 8, 9, 10, 11), X10 = c(2, 3, 4, 5, 6, 7, 8, 9, 
    10, 11), X11 = c(2, 3, 4, 5, 6, 7, 8, 9, 10, 11), X12 = c(2, 
    3, 4, 5, 6, 7, 8, 9, 10, 11), X13 = c(2, 3, 4, 5, 6, 7, 8, 
    9, 10, 11), X14 = c(2, 3, 4, 5, 6, 7, 8, 9, 10, 11), X15 = c(2, 
    3, 4, 5, 6, 7, 8, 9, 10, 11)), class = "data.frame", row.names = c(NA, 
-10L))))
Related