我的数据框看起来像:
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
感谢任何帮助。
答案 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,...)
。
或者,我会建议使用sapply
和rowSums
结合的辅助函数(将在sapply
矩阵输出上运行)
f <- function(x, y) rowSums(sapply(x, `%in%`, y))
然后你可以做(不计算A
和B
)
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