2016-07-14 79 views
1

我有一个包含30个变量的数据集。其中之一是一个指示变量(0或1),我想减去那些行的标签为1的行的平均值(类似于居中,但取某些行的平均值而不是整列)。使用summarise_each减去某些行的平均值

Col2 Col3 Col4 label 
400 322 345 1  
131 345 809 1  
565 676 311 0  
121 645 777 0  
322 534 263 0  
545 222 111 0  

对于上述数据集,我想为Col2:Col4执行以下操作:

x(i,j)-x'(,j) 

其中x(i,j)代表的细胞,和x'(,j)代表行的在列的平均值为哪些label=1 。对于e.g,为[3,1]应该

(565-mean(400,131))= 299.5

的第2列的预期输出:

Col2 
134.5 
-134.5 
299.5 
-144.5 
56.5 
279.5 

我一直在尝试使用summarise_each命令,但没有成功到现在。我给的命令是

try<- group_by(data,lbl) %>% select(c(4,13:26)) %>% summarise_each(funs((.)-(mean(data[data$lbl==1,]))) 

但这产生NA,我真的不知道我要去哪里错了(我敢肯定,这在summarise_each命令,其中我不能图了解如何正确使用funs()

任何帮助表示赞赏。谢谢!

+1

请阅读有关的信息[如何问一个好问题](http://stackoverflow.com/help/how-to-ask)以及如何给出一个[可重现的例子](http:// s tackoverflow.com/questions/5963269/how-to-make-a-great-r-reproducible-example/5963610)。这会让其他人更容易帮助你。 – Jaap

+0

@ProcrastinatusMaximus我编辑了这个问题,我希望这可以让它更清晰。谢谢! –

+0

你想要列的平均值,但没有值'标签== 1'? –

回答

2
dat %>% 
    mutate_each(funs(. - mean(.[label==1])), -label) 
Col2 Col3 Col4 label 
1 134.5 -11.5 -232  1 
2 -134.5 11.5 232  1 
3 299.5 342.5 -266  0 
4 -144.5 311.5 200  0 
5 56.5 200.5 -314  0 
6 279.5 -111.5 -466  0 
+0

哇。 Touché!非常聪明的做法。 –

+0

谢谢......史蒂文! – eipi10

1

这是我会怎么做:

sweep(df[1:3], 2, colMeans(df[df$label == 1,][1:3])) 

其中给出:

# Col2 Col3 Col4 
#1 134.5 -11.5 -232 
#2 -134.5 11.5 232 
#3 299.5 342.5 -266 
#4 -144.5 311.5 200 
#5 56.5 200.5 -314 
#6 279.5 -111.5 -466 

另一种方法(当然更令人费解):

library(purrr) 

df %>% 
    by_row(function(x) { 
    x[1:3] - df %>% 
     filter(label == 1) %>% 
     summarise_each(funs(mean), -label) }, 
    .collate = "cols", 
    .labels = FALSE 
) 

也许是最dplyr -esque方法(通过此post启发):

cm <- df %>% 
    filter(label == 1) %>% 
    summarise_each(funs(mean), -label) 

df %>% 
    mutate_each(funs(. - cm$.), -label) 

其中给出:

# Col2 Col3 Col4 label 
#1 134.5 -11.5 -232  1 
#2 -134.5 11.5 232  1 
#3 299.5 342.5 -266  0 
#4 -144.5 311.5 200  0 
#5 56.5 200.5 -314  0 
#6 279.5 -111.5 -466  0