从R数据框中提取复杂子集

4

我有一个数据集,如下所示:

testdata <- read.table(header=T, text='
patids labels dbins vprobs Response 
16186 SUP0         0.0         100        1 
16186 SUP0         0.2         99        1 
16186 SUP0         0.4         95        1 
16186 SUP0         0.6         99        1 
16186 SUP0         0.8         50        1 
16186 SUP0         1.0         0        1 
18185 SUP0         0.0         100        0 
18185 SUP0         0.2         100        0 
18185 SUP0         0.4         5        0 
18185 SUP0         0.6         2        0 
18185 SUP0         0.8         0        0 
54234 INF0         0.0         100        1 
54234 INF0         0.2         95        1 
54234 INF0         0.4         90        1 
54234 INF0         0.6         30        1 
54234 INF0         0.8         0        1 
18185 INF0         0.0         100        0 
18185 INF0         0.2         20        0 
18185 INF0         0.4         10        0 
18185 INF0         0.6         5        0 
18185 INF0         0.8         3        0 
18185 INF0         1.0         0        0 
16186 INF0         0.0         100        1 
16186 INF0         0.2         100        1 
16186 INF0         0.4         70        1 
16186 INF0         0.6         60        1 
16186 INF0         0.8         50        1 
16186 INF0         1.0         0        1 
54234 SUP1         0.0         100        1 
54234 SUP1         0.2         95        1 
54234 SUP1         0.4         90        1 
54234 SUP1         0.6         30        1 
54234 SUP1         0.8         0        1 
18185 SUP1         0.0         100        0 
18185 SUP1         0.2         50        0 
18185 SUP1         0.4         0        0
16186 SUP1         0.0         100        1 
16186 SUP1         0.2         100        1 
16186 SUP1         0.4         40        1 
16186 SUP1         0.6         10        1 
16186 SUP1         0.8         22        1 
16186 SUP1         1.0         0        1 ')

现在,对于每个“标签”,即SUP0、SUP1等,我想要获得变量dbins的平均值(取所有唯一的“patids”变量的平均值)。我面临的问题是,对于每个“patids”,“dbins”的长度并不相同。是否有一种方法可以在取平均值之前填充NA或0?我的预期输出应该像这样:
对于SUP0
labels dbins dbins.16186 dbins.18185
SUP0         0.0         0.0 
SUP0         0.2         0.2          
SUP0         0.4         0.4          
SUP0         0.6         0.6          
SUP0         0.8         0.8          
SUP0         1.0         NA 

并且针对INF0

labels      dbins.54234 dbins.18185 dbins.16186
INF0         0.0         0.0        0.0    0.0    
INF0         0.2         0.2        0.0    0.2   
INF0         0.4         0.4        0.0    0.4   
INF0         0.6         0.6        0.0    0.6   
INF0         0.8         0.8        0.8    0.8   
INFO         NA          1.0        1.0    1.0 

我希望能够对列进行平均值计算,涉及到it技术相关内容。我尝试使用ddply和类似的函数,但是无法得到这种特定的输出格式。请问有人可以帮忙吗?

提前感谢。

4个回答

3
您想要的答案可能是以下两种之一:
  1. 您提供的确切输出。

  2. 每个类别的方法(您提供的输出只是到达目标的方法之一)

我将使用plyr和reshape2,但毫无疑问@mnel很快就会提供一个data.table解决方案。

1. 您提供的确切输出

问题在于您有多个元素的几个组。因此,首先我们需要对元素进行分组(使用@Maiasaura的解决方案here)。
library(plyr)
testgroups <- ddply(testdata, .(labels, patids), function(x) { x$group <- 1:nrow(x); x })

然后我们可以适当地重新塑造它们:
library(reshape2)
testreshape <- dcast(testgroups[,c("labels", "patids", "dbins", "group")], labels+group~patids, value.var="dbins")

   labels group 16186 18185 54234
1    INF0     1   0.0   0.0   0.0
2    INF0     2   0.2   0.2   0.2
3    INF0     3   0.4   0.4   0.4
4    INF0     4   0.6   0.6   0.6
5    INF0     5   0.8   0.8   0.8
6    INF0     6   1.0   1.0    NA
7    SUP0     1   0.0   0.0    NA
8    SUP0     2   0.2   0.2    NA
9    SUP0     3   0.4   0.4    NA
10   SUP0     4   0.6   0.6    NA
11   SUP0     5   0.8   0.8    NA
12   SUP0     6   1.0    NA    NA
13   SUP1     1   0.0   0.0   0.0
14   SUP1     2   0.2   0.2   0.2
15   SUP1     3   0.4   0.4   0.4
16   SUP1     4   0.6    NA   0.6
17   SUP1     5   0.8    NA   0.8
18   SUP1     6   1.0    NA    NA

从这里开始,您可以使用类似于testreshape[testreshape$labels=="INF0",]的内容。

2. 每个类别的平均值

这要简单得多:

library(plyr)
testmeans <- ddply(testdata, .(labels, patids), summarise, mean=mean(dbins, na.rm=TRUE))

  labels patids mean
1   INF0  16186  0.5
2   INF0  18185  0.5
3   INF0  54234  0.4
4   SUP0  16186  0.5
5   SUP0  18185  0.4
6   SUP1  16186  0.5
7   SUP1  18185  0.2
8   SUP1  54234  0.4

2

使用专门针对不规则数组的tapply直接计算每个类别的均值:

tapply(testdata$dbins, interaction(testdata$labels, testdata$patid, drop=TRUE), FUN=mean)
## INF0.16186 SUP0.16186 SUP1.16186 INF0.18185 SUP0.18185 SUP1.18185 INF0.54234 SUP1.54234 
##        0.5        0.5        0.5        0.5        0.4        0.2        0.4        0.4 

也就是:tapply(testdata[,"dbins"], testdata[c("patids","labels")], FUN=mean) - IRTFM

1

为了直接的手段:

> require(data.table)
> testdata <- as.data.table(testdata)
> testdata[, mean(dbins), by=c("patids","labels")]
   patids labels  V1
1:  16186   SUP0 0.5
2:  18185   SUP0 0.4
3:  54234   INF0 0.4
4:  18185   INF0 0.5
5:  16186   INF0 0.5
6:  54234   SUP1 0.4
7:  18185   SUP1 0.2
8:  16186   SUP1 0.5
> 

1
我想获取变量dbins的平均值(在所有唯一的“patids”变量上取平均值)。
使用data.table。
R) library(data.table)
R) testdata=as.data.table(testdata)
R) testdata
    patids labels dbins vprobs Response
 1:  16186   SUP0   0.0    100        1
 2:  16186   SUP0   0.2     99        1
 3:  16186   SUP0   0.4     95        1
---
40:  16186   SUP1   0.6     10        1
41:  16186   SUP1   0.8     22        1
42:  16186   SUP1   1.0      0        1
    patids labels dbins vprobs Response

R) testdata[,list(dbins=mean(dbins)),by="patids"]
   patids dbins
1:  16186   0.5
2:  18185   0.4
3:  54234   0.4

几乎,但它没有回答问题中的细微之处(所需输出),如果我理解正确。 - Matt Dowle

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接