具有动态维度

时间:2017-03-02 18:10:56

标签: arrays r

我想将具有动态维数k的数组子集化。

举个例子:

A <- array(1:3^4, dim=c(3,3,3,3))

因为尺寸可能会有所不同(此处未显示),所以我不能简单地定义a,b,c,d并通过

进行查询
a <- 1:2; b <- 2; c <- 2:3; d = 1
A[a, b, c, d]

Here已经证明,如果想要将只有一个元素的子集,那么可以这样做:

e <- 1; f <- 2; g <- 3; h <- 1
A[matrix(c(e, f, g, h), nrow = 1)]

这允许我保持多个维度的灵活性,但我只能将单个元素子集化,因为我无法在矩阵中表示序列a,b,c,d。

期望的情况是我可以得到

的输出
A[a, b, c, d]

没有硬编码尺寸,即通过

访问数组
A[object]

问题基本上是可能的,如果是的话,对象&#39;看起来像。

非常感谢任何帮助!

2 个答案:

答案 0 :(得分:2)

如果您将object定义为列表,则可以使用do.call将该列表用作子集化函数[的参数。如果您将数组作为列表中的第一项,则可以直接调用[

object <- list(A, a, b, c, d)

do.call(`[`, object)
##      [,1] [,2]
## [1,]   13   22
## [2,]   14   23

如果你不想包含数组(如果你有很多这些对象并且数组很大,则需要大量内存),你可以编写一个匿名函数来只使用子集化参数,不是什么是子集:

object <- list(a, b, c, d)

do.call(function(...){A[...]}, object)
##      [,1] [,2]
## [1,]   13   22
## [2,]   14   23

这实际上是abind::asub所采用的确切方法:

object <- list(a, b, c, d)

abind::asub(A, object)
##      [,1] [,2]
## [1,]   13   22
## [2,]   14   23

请注意,此处的参数匹配是关系,因此如果一个为空,则需要包含NULL

object <- list(NULL, b, c, d)

abind::asub(A, object)
##      [,1] [,2]
## [1,]   13   22
## [2,]   14   23
## [3,]   15   24

答案 1 :(得分:1)

我之前遇到过这种情况,并发现了这种(快速和肮脏)方式来获取任意设置向量并获取数据。数组允许您传递值矩阵,其中每行代表数组中的一个位置。因此,我使用expand.grid来获取我想要查看的子集向量的所有组合,并使用此事实来获取我想要的值:

A <- array(1:3^4, dim=c(3,3,3,3))
a <- 1:2; b <- 2; c <- 2:3; d = 1

eg<- expand.grid(a,b,c,d)
mat <- as.matrix(eg)

print(A[mat]) 
[1] 13 14 22 23