求R函数熔化5维数组,比如pivot_longer
Seeking R function to melt 5-dimensional array, like pivot_longer
我有一个程序使用 reshape2 的 melt 函数将具有命名和标记维度的 5 维数组融合为长格式数据框,根据定义,它只有两个维度。输入数组的每个维度对应于输出数据框中的一列,并且还有一列保存存储在 5D 数组中的值。
我知道 reshape2 已被弃用,很快就会失效。所以我要改用 tidyr。然而,替代 melt 的 tidyr pivot_longer 函数仅接受 2D 数据帧作为输入。
在 tidyr 或其他地方是否有一个未弃用的函数,它会将具有 3 个或更多命名和标记维度的数组融化为长格式数据框?
我可以编写自己的函数来轻松完成。但如果有的话,我宁愿使用现有的功能。
谢谢
这是一个 2x3x4 数组的示例:
df <- expand.grid(w = 1:2,
x = 1:3,
y = 1:4)
df$z <- runif(nrow(df))
tmp <- tapply(df$z, list(df$w, df$x, df$y), sum)
tmp
, , 1
1 2 3
1 0.40276418 0.13111652 0.4473557
2 0.08945365 0.03139184 0.1556355
, , 2
1 2 3
1 0.1413763 0.02106974 0.1103559
2 0.7302435 0.46302772 0.7924580
, , 3
1 2 3
1 0.2793435 0.4244807 0.7955351
2 0.9828739 0.7740189 0.6436733
, , 4
1 2 3
1 0.9852345 0.20508490 0.8744829
2 0.2812744 0.06272449 0.0936831
坚持使用基数 R,您可以在使用 as.data.frame
之前将数组包装在 ftable
中:
set.seed(1); array(sample(100, 2*3*4, TRUE), dim = c(2, 3, 4)) -> a
b <- provideDimnames(a)
b
# , , A
#
# A B C
# A 27 58 21
# B 38 91 90
#
# , , B
#
# A B C
# A 95 63 21
# B 67 7 18
#
# , , C
#
# A B C
# A 69 77 72
# B 39 50 100
#
# , , D
#
# A B C
# A 39 94 66
# B 78 22 13
as.data.frame(ftable(b))
# Var1 Var2 Var3 Freq
# 1 A A A 27
# 2 B A A 38
# 3 A B A 58
# 4 B B A 91
# 5 A C A 21
# 6 B C A 90
# 7 A A B 95
# 8 B A B 67
# 9 A B B 63
# 10 B B B 7
# 11 A C B 21
# 12 B C B 18
# 13 A A C 69
# 14 B A C 39
# 15 A B C 77
# 16 B B C 50
# 17 A C C 72
# 18 B C C 100
# 19 A A D 39
# 20 B A D 78
# 21 A B D 94
# 22 B B D 22
# 23 A C D 66
# 24 B C D 13
您还可以使用“data.table”包中的 as.data.table
。以下应该有效:
library(data.table)
as.data.table(b)
我有一个程序使用 reshape2 的 melt 函数将具有命名和标记维度的 5 维数组融合为长格式数据框,根据定义,它只有两个维度。输入数组的每个维度对应于输出数据框中的一列,并且还有一列保存存储在 5D 数组中的值。
我知道 reshape2 已被弃用,很快就会失效。所以我要改用 tidyr。然而,替代 melt 的 tidyr pivot_longer 函数仅接受 2D 数据帧作为输入。
在 tidyr 或其他地方是否有一个未弃用的函数,它会将具有 3 个或更多命名和标记维度的数组融化为长格式数据框?
我可以编写自己的函数来轻松完成。但如果有的话,我宁愿使用现有的功能。
谢谢
这是一个 2x3x4 数组的示例:
df <- expand.grid(w = 1:2,
x = 1:3,
y = 1:4)
df$z <- runif(nrow(df))
tmp <- tapply(df$z, list(df$w, df$x, df$y), sum)
tmp
, , 1
1 2 3
1 0.40276418 0.13111652 0.4473557
2 0.08945365 0.03139184 0.1556355
, , 2
1 2 3
1 0.1413763 0.02106974 0.1103559
2 0.7302435 0.46302772 0.7924580
, , 3
1 2 3
1 0.2793435 0.4244807 0.7955351
2 0.9828739 0.7740189 0.6436733
, , 4
1 2 3
1 0.9852345 0.20508490 0.8744829
2 0.2812744 0.06272449 0.0936831
坚持使用基数 R,您可以在使用 as.data.frame
之前将数组包装在 ftable
中:
set.seed(1); array(sample(100, 2*3*4, TRUE), dim = c(2, 3, 4)) -> a
b <- provideDimnames(a)
b
# , , A
#
# A B C
# A 27 58 21
# B 38 91 90
#
# , , B
#
# A B C
# A 95 63 21
# B 67 7 18
#
# , , C
#
# A B C
# A 69 77 72
# B 39 50 100
#
# , , D
#
# A B C
# A 39 94 66
# B 78 22 13
as.data.frame(ftable(b))
# Var1 Var2 Var3 Freq
# 1 A A A 27
# 2 B A A 38
# 3 A B A 58
# 4 B B A 91
# 5 A C A 21
# 6 B C A 90
# 7 A A B 95
# 8 B A B 67
# 9 A B B 63
# 10 B B B 7
# 11 A C B 21
# 12 B C B 18
# 13 A A C 69
# 14 B A C 39
# 15 A B C 77
# 16 B B C 50
# 17 A C C 72
# 18 B C C 100
# 19 A A D 39
# 20 B A D 78
# 21 A B D 94
# 22 B B D 22
# 23 A C D 66
# 24 B C D 13
您还可以使用“data.table”包中的 as.data.table
。以下应该有效:
library(data.table)
as.data.table(b)