当我想要携带多个度量变量时,我无法找出将数据从长格式切换到宽格式的最优雅和最灵活的方法。
例如,这是一个长格式的简单数据框。 ID
是主体,TIME
是时间变量,X
和 Y
是 ID
在 TIME
处的测量值:
> my.df <- data.frame(ID=rep(c("A","B","C"), 5), TIME=rep(1:5, each=3), X=1:15, Y=16:30)
> my.df
ID TIME X Y
1 A 1 1 16
2 B 1 2 17
3 C 1 3 18
4 A 2 4 19
5 B 2 5 20
6 C 2 6 21
7 A 3 7 22
8 B 3 8 23
9 C 3 9 24
10 A 4 10 25
11 B 4 11 26
12 C 4 12 27
13 A 5 13 28
14 B 5 14 29
15 C 5 15 30
如果我只想将
TIME
的值转换为包含 include X
的列标题,我知道我可以使用 cast()
包中的 reshape
(或 dcast()
中的 0x1045 )6:> cast(my.df, ID ~ TIME, value="X")
ID 1 2 3 4 5
1 A 1 4 7 10 13
2 B 2 5 8 11 14
3 C 3 6 9 12 15
但我真正想做的是将
reshape2
作为另一个度量变量,并让列名同时反射(reflect)度量变量名称和时间值: ID X_1 X_2 X_3 X_4 X_5 Y_1 Y_2 Y_3 Y_4 Y_5
1 A 1 4 7 10 13 16 19 22 25 28
2 B 2 5 8 11 14 17 20 23 26 29
3 C 3 6 9 12 15 18 21 24 27 30
(FWIW,我真的不在乎所有
Y
是否首先跟在 X
之后,或者它们是否交错为 Y
、 X_1
、 Y_1
、4,567914 10我可以通过两次转换长数据并合并结果来接近这一点,尽管列名需要一些工作,如果除了
X_2
和 Y_2
之外我还需要添加第三个或第四个变量,我需要调整它:merge(
cast(my.df, ID ~ TIME, value="X"),
cast(my.df, ID ~ TIME, value="Y"),
by="ID", suffixes=c("_X","_Y")
)
似乎
X
和/或 Y
中的一些函数组合应该能够比我的尝试更优雅地做到这一点,以及更干净地处理多个度量变量。类似 reshape2
的东西,这是无效的。但我一直无法弄清楚。
最佳答案
为了处理您想要的多个变量,您需要melt
您在转换之前拥有的数据。
library("reshape2")
dcast(melt(my.df, id.vars=c("ID", "TIME")), ID~variable+TIME)
这使
ID X_1 X_2 X_3 X_4 X_5 Y_1 Y_2 Y_3 Y_4 Y_5
1 A 1 4 7 10 13 16 19 22 25 28
2 B 2 5 8 11 14 17 20 23 26 29
3 C 3 6 9 12 15 18 21 24 27 30
根据评论编辑:
数据框
num.id = 10
num.time=10
my.df <- data.frame(ID=rep(LETTERS[1:num.id], num.time),
TIME=rep(1:num.time, each=num.id),
X=1:(num.id*num.time),
Y=(num.id*num.time)+1:(2*length(1:(num.id*num.time))))
给出不同的结果(所有条目都是 2),因为
ID
/TIME
组合并不表示唯一的行。实际上,有两行,每行 ID
/TIME
组合。 reshape2
假设变量的每个可能组合都有一个值,并且如果有多个条目,将应用汇总函数来创建单个变量。这就是为什么有警告Aggregation function missing: defaulting to length
如果您添加另一个破坏冗余的变量,您可以获得一些有效的东西。
my.df$cycle <- rep(1:2, each=num.id*num.time)
dcast(melt(my.df, id.vars=c("cycle", "ID", "TIME")), cycle+ID~variable+TIME)
这是有效的,因为
cycle
/ID
/time
现在唯一地定义了 my.df
中的一行.
关于r - 使用多个度量列将数据从长格式转换为宽格式,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/10589693/