R中的多维数组是否有一个inner_join等效项?

问题描述 投票:0回答:1

对于3d数组是否有某种inner_join等效项,可以将2d结构连接到3d结构吗?

让我们看看这是否有意义:

我有一个3d整数数组(微生物组计数数据)。

  • 维度1:复制1:100
  • 维度2:样本
  • 第3维:分类单元

我有一个二维元数据表。

  • 维度1:样本
  • 维度2:元数据类型(稀释,采样日期等)

[2d元数据表中有一列(样本名称)与数组中第二维的标签匹配。

我可以以某种方式将两者结合在一起,以便保留数组结构并为每个样本添加元数据吗?

我是否必须将数组融化/堆叠成超长的2d表?

感谢您的帮助!

-编辑

假设我使用以下代码生成数组a和“ a”表“ b”:

a <- array(1:10,c(2,4,3))
b <- data.frame("thing" = c("stuff", "foo", "dodad"), "data" = c(10,20,30), "match" = c("first","second","third"))
dimnames(a) <- list(c("A", "B"), c("one", "two", "three", "four"), c("first", "second", "third"))

如您所见,我在表“ b”中有一个列“ match”,我想将其与维名称a [[3]]联接/匹配。

所以,如果我们看“ a”和“ b”

> a
, , first

  one two three four
A   1   3     5    7
B   2   4     6    8

, , second

  one two three four
A   9   1     3    5
B  10   2     4    6

, , third

  one two three four
A   7   9     1    3
B   8  10     2    4

> b
  thing data  match
1 stuff   10  first
2   foo   20 second
3 dodad   30  third

例如,我想要数组

, , third

      one two three four
    A   7   9     1    3
    B   8  10     2    4

具有与标签“ thing”和“ data”相关联的元素“ dodad”和“ 30”。

对于真实数据集,我希望使用“患者姓名”代替“事物”,使用“稀释”代替“数据”,并使用这些元素作为从切片中拉出切片以进行统计分析的方法。

r arrays inner-join metadata
1个回答
0
投票

您没有显示您想要的输出,所以我猜。

[如果从a(具有AxBxC暗点)和b(具有DxE暗点,则应该获得具有AxBxD暗点的数组。

a[,,b[,"match"]]
# , , first
#   one two three four
# A   1   3     5    7
# B   2   4     6    8
# , , second
#   one two three four
# A   9   1     3    5
# B  10   2     4    6
# , , third
#   one two three four
# A   7   9     1    3
# B   8  10     2    4

就组合输出而言,使用您提供的数据不会发生:矩阵a具有所有数据必须为同一类的约束,而b是具有不同类的帧。因此,如果您需要将数字保留在a中,将字符串或因子保留在b中,则不能仅将一个合并到另一个。

您有一些选择:

  1. 如果您的第二帧确实可以是矩阵,那么我们可以做到这一点。

    ### a naive conversion, your case may vary with real data
    bnum <- sapply(b, as.integer)
    dim(bnum) <- c(dim(bnum), 1)
    dimnames(bnum) <- list(rownames(b), colnames(b), NULL)
    bnum
    # , , 1
    #   thing data match
    # 1     3   10     1
    # 2     2   20     2
    # 3     1   30     3
    
    ### the solution
    abind::abind(
      apply(bnum[,-3,1], 2:1, rep, times = dim(a)[1]),
      a[,,bnum[,"match",1]],
      along = 2
    )
    # , , first
    #   thing data one two three four
    # A     3   10   1   3     5    7
    # B     3   10   2   4     6    8
    # , , second
    #   thing data one two three four
    # A     2   20   9   1     3    5
    # B     2   20  10   2     4    6
    # , , third
    #   thing data one two three four
    # A     1   30   7   9     1    3
    # B     1   30   8  10     2    4
    
  2. 如果您需要保持b不变,则无法制作3维数组。一种选择是以列表列的方式嵌套a的每一层。

    out <- within(b, { mtx = lapply(match, function(m) a[,,m]) })
    out
    #   thing data  match                     mtx
    # 1 stuff   10  first  1, 2, 3, 4, 5, 6, 7, 8
    # 2   foo   20 second 9, 10, 1, 2, 3, 4, 5, 6
    # 3 dodad   30  third 7, 8, 9, 10, 1, 2, 3, 4
    

    虽然看起来好像丢失了a的z层的布局,但这在控制台上的表现很差。还是不错的:

    out$mtx[[1]]
    #   one two three four
    # A   1   3     5    7
    # B   2   4     6    8
    

    如果您有兴趣,也可以使用dplyrdata.table完成。

    library(dplyr)
    out <- b %>%
      mutate(mtx = lapply(match, function(m) a[,,m]))
    # option to use purrr::map instead of lapply
    
    library(data.table)
    out <- as.data.table(b)[, mtx := lapply(match, function(m) a[,,m]) ]
    
© www.soinside.com 2019 - 2024. All rights reserved.