Sapply或for循环在数据集上应用grepl函数?

时间:2015-03-09 07:05:56

标签: r function

我正在寻找最优雅的方法来替换数据集的32列中的值,目前所有这些都存储为因子。看起来像这样:

   GENT CIP LEVO CB CT CTX
138                        
145        R          S    
156    S   S    S          
161    S   S    S          
173                        

正如你所看到的,有R,S和很多空间...... R需要'抗拒','需要'敏感',空间需要保持原样。

以下单个变量的效果非常好(感谢那些回答我最后一个问题的人提供的信息!!):

x <- as.character(drugs$CIP)
new <- rep(NA, length(x))
new[grepl("R", x)] <- "RESISTANT"
new[grepl("S", x)] <- "SENSITIVE"

问题是,如何一次在数据集的所有列上应用它?认为可能有一个sapply解决方案,或者要编写的循环,我确信答案很简单,但我不习惯编写函数,所以发现自己被卡住了......再次感谢所有人你的帮助!!

尝试了一个嵌套的'ifelse'语句:

drugs[2:33]<-ifelse(drugs[3:33] == 'R', 'RESISTANT', ifelse(drugs[3:33] == 
'S', 'SENSITIVE', ifelse(drugs[3:33] == "", "", "")))

并收到以下内容。

  

[<-.data.frame中的错误(*tmp*,2:33,值= c(“”,“”,“”,“”,“”,     更换有2325项,需要2400

更新:根据要求发布了样本数据,并且正在弄乱一些答案......还没有完成任何工作,但我认为我的错误是一个不明确的问题。非常感谢帮助!!谢谢,stackoverflow。

2 个答案:

答案 0 :(得分:1)

如果数据类似于我创建的数据,并假设每个列只有三个级别(RS'')(3:33) 。

 drugs[3:33] <-  ifelse(drugs[3:33] =='R', 'RESISTANT', 
                    ifelse(drugs[3:33]=='S', 'SENSITIVE', ''))

或者

 drugs[,3:33] <- `dim<-`(factor(as.matrix(drugs[3:33]), 
     levels=c('', 'S', 'R'), labels=c('', 'SENSITIVE', 'RESISTANT')),
                   dim(drugs2[3:33]))

大数据集的另一个选项是使用data.table

library(data.table)
setDT(drugs)[, 3:33 := lapply(.SD, function(x) factor(x, 
    levels=c('', 'S', 'R'), labels=c('', 'SENSITIVE', 'RESISTANT'))),
       .SDcols=3:33][]

或者可能更快的选择是使用for循环set

setDT(drugs)
for(j in 3:33){
  set(drugs, i=NULL, j=j, value= factor(drugs[[j]], levels=c('', 'S', 'R'),
          labels=c('', 'SENSITIVE', 'RESISTANT')))
 }

数据

set.seed(35)
m1 <- matrix(sample(c('R', 'S', ''), 10*31, replace=TRUE), ncol=31)
drugs <- data.frame(id=1:10, Someval=rnorm(10), m1)

答案 1 :(得分:0)

使用dplyrtidyr,您可以实现以下两种方式之一:

1)tidyr :: gather()要将名称重新编码为两列keyvalue的列,重新编码value变量,然后使用tidyr :: spread()将值传播回单独的列。

2)使用函数dplyr :: mutate_each()。

如果您想要使用其中一种或两种方法的示例代码,请告诉我。希望只知道有这两种简单的方法是有用的,使用它只需几分钟即可实现所需的输出。