基于r

时间:2016-01-07 14:40:47

标签: r

我的数据框看起来像:

df = read.table(text="S00001    S00002  S00003  S00004  S00005  S00006  
GG  AA  GG  AA  GG  AG  
CC  TT  TT  TC  TC  TT  
TT  CC  CC  TT  TT  TT  
AA  AA  GG  AA  AG  AA  
TT  CC  CC  TT  TC  TT  
GG  GG  GG  AA  GG  GG", header=T, stringsAsFactors=F)

我想计算每行具有相同字母(即“AA”,“CC”,“GG”或“TT”)的字符串的数量。我所做的是使用table()函数来计算所有元素,并根据列表的名称是否为“homo”生成另一个列表。我试图将列表分组,但它没有用。这是我的脚本:

A <- apply(df,1, function(x) table(x))
B <- apply(df,1, function(x) (names(table(x)) %in% c("AA","CC","GG","TT")))
A[B] ## this didn't work

我希望会生成一个数据框:

2 3
1 3
2 4
4 1
2 3
1 5

感谢任何帮助。

3 个答案:

答案 0 :(得分:4)

试试mapply。它将依次采用列表中的每个元素进行评估。标题名称是自动生成的,您可以根据需要更改它们:

t(mapply('[', A, B))
     AA GG
[1,]  2  3
[2,]  1  3
[3,]  2  4
[4,]  4  1
[5,]  2  3
[6,]  1  5

如CathG所述,您可以避免使用以下内容计算B

t(sapply(A, function(x){x[grepl("([A-Z])\\1", names(x))]}))

答案 1 :(得分:3)

由于矩阵转换,我不喜欢apply,尤其是因行操作而导致apply(df, 1,...)

或者,我会建议使用sapplyrowSums结合的辅助函数(将在sapply矩阵输出上运行)

f <- function(x, y) rowSums(sapply(x, `%in%`, y))

然后你可以做(​​不计算AB

cbind(f(df, c("AA", "CC")), 
      f(df, c("GG", "TT")))
#      [,1] [,2]
# [1,]    2    3
# [2,]    1    3
# [3,]    2    4
# [4,]    4    1
# [5,]    2    3
# [6,]    1    5

或者只是(取决于你要找的东西)

f(df, c("AA", "CC", "GG", "TT"))
# [1] 5 4 6 5 5 6

答案 2 :(得分:3)

我们可以使用一个apply

来完成此操作
t(apply(df, 1, function(x) {tbl <- table(x)
        tbl[names(tbl) %in% c("AA", "CC", "GG", "TT")]}))
#      [,1] [,2]
#[1,]    2    3
#[2,]    1    3
#[3,]    2    4
#[4,]    4    1
#[5,]    2    3
#[6,]    1    5