从满足给定条件的变量名称生成变量

时间:2018-01-16 16:54:44

标签: r

这是我数据的一小部分。我有超过2万个变量和700个变量。我想要做的是获取变量的子集,并创建一个新变量,该变量具有该子集的变量名称,其值为1. 这些子集中的所有变量都将是字符变量。

     id gen16 gen18 gen31 gen33 gen35 gen39 gen45 gen51 gen52 gen56 gen58 gen59 gen66 gen68
5962  1     1     2     2     2     2     2     2     2     1     2     2     2     1     2
6085  2     2     2     2     2     2     2     2     2     2     2     1     2     2     2
6183  3     1     2     2     2     2     2     2     2     2     2     2     2     2     2
6386  4     1     2     2     2     2     2     2     2     2     2     2     2     2     2
6989  5     1     2     1     2     2     2     2     2     2     2     2     2     2     2
7057  6     2     1     1     2     2     2     1     2     2     2     2     2     2     2
7276  7     2     2     2     2     2     2     2     1     1     2     2     2     1     2
7748  8     2     1     2     2     2     2     2     1     2     2     2     2     2     2
7917  9     2     2     2     2     2     2     2     1     2     2     2     2     2     2
8654 10     2     2     2     2     2     2     2     2     2     2     2     1     2     2

所以这就是我要找的。

     id gen16 gen18 gen31 gen33 gen35 gen39 gen45 gen51 gen52 gen56 gen58 gen59 gen66 gen68                  V1
5962  1     1     2     2     2     2     2     2     2     1     2     2     2     1     2 gen16, gen52, gen66
6085  2     2     2     2     2     2     2     2     2     2     2     1     2     2     2               gen58
6183  3     1     2     2     2     2     2     2     2     2     2     2     2     2     2               gen16
6386  4     1     2     2     2     2     2     2     2     2     2     2     2     2     2               gen16
6989  5     1     2     1     2     2     2     2     2     2     2     2     2     2     2        gen16, gen31
7057  6     2     1     1     2     2     2     1     2     2     2     2     2     2     2 gen18, gen31, gen45
7276  7     2     2     2     2     2     2     2     1     1     2     2     2     1     2 gen51, gen52, gen66
7748  8     2     1     2     2     2     2     2     1     2     2     2     2     2     2        gen18, gen51
7917  9     2     2     2     2     2     2     2     1     2     2     2     2     2     2               gen51
8654 10     2     2     2     2     2     2     2     2     2     2     2     1     2     2               gen59

我已经编写了一个执行此操作的for循环,但我想避免循环,因为我的数据集只会变大。我的想法是编写一个适用于一行的函数,然后使用apply函数在整个数据集上迭代它。我很幸运获得了两行不同的功能,但在尝试在apply函数中使用它们时会遇到问题。

这是我写的另外两个函数。

inf.type <- function(x) {
  foo <- as.data.frame(x[, c("gen16", "gen18", "gen31", "gen33", "gen35",
"gen39", "gen45", "gen51", "gen52", "gen56", "gen58", "gen59", "gen66", "gen68")] == 1)
  gentypes <- paste(names(foo[colSums(foo) == "1"]), collapse = ", ")

  return(gentypes)
}

inf.type <- function(x) {
  foo <- x[, c("gen16", "gen18", "gen31", "gen33", "gen35", "gen39", "gen45", 
              "gen51", "gen52", "gen56", "gen58", "gen59", "gen66", "gen68")]
  return(paste(names(foo[grep("1", foo)]), collapse = ", "))
 }

这两个似乎适用于单行,但不适用于使用apply函数的情况。如果有人可以帮我弄清楚如何让其中一个在apply函数中工作,或者对一个完全不同的方法有更好的建议,我将不胜感激。

1 个答案:

答案 0 :(得分:3)

这应该完成工作:

df$V1 = apply(df[,-1], 1, function(x) paste(names(which(x=='1')), collapse = ", "))

查看df[,-1]的每一行(不包括id列),返回与which匹配的索引(x=='1'}),提取names对应于那些索引,paste每行的名称。

还可以写下以下内容(使用@ alistaire&#39;建议):

df$V1 = apply(df[, -1] == 1, 1, function(x) toString(names(x)[x]))

df[, -1] == 1df[, -1]转换为逻辑矩阵,如果它等于TRUE,则每个单元格评估为1,否则为FALSE。然后,可以为每行提取namesTRUE个单元格,然后将这些名称与toString连接起来。

<强>结果:

     id gen16 gen18 gen31 gen33 gen35 gen39 gen45 gen51 gen52 gen56 gen58 gen59
5962  1     1     2     2     2     2     2     2     2     1     2     2     2
6085  2     2     2     2     2     2     2     2     2     2     2     1     2
6183  3     1     2     2     2     2     2     2     2     2     2     2     2
6386  4     1     2     2     2     2     2     2     2     2     2     2     2
6989  5     1     2     1     2     2     2     2     2     2     2     2     2
7057  6     2     1     1     2     2     2     1     2     2     2     2     2
7276  7     2     2     2     2     2     2     2     1     1     2     2     2
7748  8     2     1     2     2     2     2     2     1     2     2     2     2
7917  9     2     2     2     2     2     2     2     1     2     2     2     2
8654 10     2     2     2     2     2     2     2     2     2     2     2     1
     gen66 gen68                  V1
5962     1     2 gen16, gen52, gen66
6085     2     2               gen58
6183     2     2               gen16
6386     2     2               gen16
6989     2     2        gen16, gen31
7057     2     2 gen18, gen31, gen45
7276     1     2 gen51, gen52, gen66
7748     2     2        gen18, gen51
7917     2     2               gen51
8654     2     2               gen59

数据:

df = structure(list(id = c("1", "2", "3", "4", "5", "6", "7", "8", 
"9", "10"), gen16 = c("1", "2", "1", "1", "1", "2", "2", "2", 
"2", "2"), gen18 = c("2", "2", "2", "2", "2", "1", "2", "1", 
"2", "2"), gen31 = c("2", "2", "2", "2", "1", "1", "2", "2", 
"2", "2"), gen33 = c("2", "2", "2", "2", "2", "2", "2", "2", 
"2", "2"), gen35 = c("2", "2", "2", "2", "2", "2", "2", "2", 
"2", "2"), gen39 = c("2", "2", "2", "2", "2", "2", "2", "2", 
"2", "2"), gen45 = c("2", "2", "2", "2", "2", "1", "2", "2", 
"2", "2"), gen51 = c("2", "2", "2", "2", "2", "2", "1", "1", 
"1", "2"), gen52 = c("1", "2", "2", "2", "2", "2", "1", "2", 
"2", "2"), gen56 = c("2", "2", "2", "2", "2", "2", "2", "2", 
"2", "2"), gen58 = c("2", "1", "2", "2", "2", "2", "2", "2", 
"2", "2"), gen59 = c("2", "2", "2", "2", "2", "2", "2", "2", 
"2", "1"), gen66 = c("1", "2", "2", "2", "2", "2", "1", "2", 
"2", "2"), gen68 = c("2", "2", "2", "2", "2", "2", "2", "2", 
"2", "2")), class = "data.frame", .Names = c("id", "gen16", "gen18", 
"gen31", "gen33", "gen35", "gen39", "gen45", "gen51", "gen52", 
"gen56", "gen58", "gen59", "gen66", "gen68"), row.names = c(NA, 
-10L))