【问题标题】:If values in a range of columns aren't present in another column, replace with NA如果某一列中的值不存在于另一列中,则替换为 NA
【发布时间】:2019-10-11 06:26:03
【问题描述】:

我有一个数据集,其中包含一些我想用 NA 替换的未引用数据。在下面的示例中,如果列 rep1 到 rep4 中的数据与 ID 列中的值之一不匹配,我想用 NA 替换该值。在这种情况下,x、y 和 z 的值未列在 ID 列中,因此应替换它们。

这是我之前在这里问过的一个有点相似的问题:If data present, replace with data from another column based on row ID

我认为解决方案将类似于上一个问题中给出的解决方案,但我不知道如何更改第二部分 ~ value[match(., ID)] 以针对 ID 列中未列出的值返回 NA。

df %>% mutate_at(vars(rep1:rep4), ~ value[match(., ID)])

ID  rep1  rep2  rep3  rep4  
a                           
b   a                       
c   a     b                 
d   a     b     c           
e   a     b     c     d     
f                           
g   x                       
h                           
i                           
j   y     z                 
k   z                       
l                           
m                           

结果应该是这样的:

ID  rep1  rep2  rep3  rep4  
a                           
b   a                       
c   a     b                 
d   a     b     c           
e   a     b     c     d     
f                           
g   NA                      
h                           
i                           
j   NA    NA                    
k   NA                      
l                           
m                           

这是使用dput()的数据

structure(list(ID = structure(1:13, .Label = c("a", "b", "c", 
"d", "e", "f", "g", "h", "i", "j", "k", "l", "m"), class = "factor"), 
    rep1 = structure(c(1L, 2L, 2L, 2L, 2L, 1L, 3L, 1L, 1L, 4L, 
    5L, 1L, 1L), .Label = c("", "a", "x", "y", "z"), class = "factor"), 
    rep2 = structure(c(1L, 1L, 2L, 2L, 2L, 1L, 1L, 1L, 1L, 3L, 
    1L, 1L, 1L), .Label = c("", "b", "z"), class = "factor"), 
    rep3 = structure(c(1L, 1L, 1L, 2L, 2L, 1L, 1L, 1L, 1L, 1L, 
    1L, 1L, 1L), .Label = c("", "c"), class = "factor"), rep4 = structure(c(1L, 
    1L, 1L, 1L, 2L, 1L, 1L, 1L, 1L, 1L, 1L, 1L, 1L), .Label = c("", 
    "d"), class = "factor")), class = "data.frame", row.names = c(NA, -13L))

【问题讨论】:

    标签: r na dplyr


    【解决方案1】:

    dplyralternative 使用 replace()

    df %>%
      mutate_at(vars(rep1:rep4), ~replace(., which(!(. %in% ID | . == "")), NA))
    
       ID rep1 rep2 rep3 rep4
    1   a                    
    2   b    a               
    3   c    a    b          
    4   d    a    b    c     
    5   e    a    b    c    d
    6   f                    
    7   g <NA>               
    8   h                    
    9   i                    
    10  j <NA> <NA>          
    11  k <NA>               
    12  l                    
    13  m 
    
    

    【讨论】:

    • 感谢您的帮助。出于好奇,如果 ID 列没有任何缺失值,那么函数 df == '' 的第二部分是否必要?
    • 这部分始终是必需的,否则您的空白字段将获得NA,因为空白不会出现在ID 列中。并且您想要的输出显示 NAonly 用于那些没有出现在 ID 并且不为空的字段。
    【解决方案2】:

    如果ID 中不存在或具有空白值,我们可以使用sapply 并将值替换为NA

    df[!(sapply(df, `%in%`, df$ID) | df == '')] <- NA
    df
    
    #   ID rep1 rep2 rep3 rep4
    #1   a                    
    #2   b    a               
    #3   c    a    b          
    #4   d    a    b    c     
    #5   e    a    b    c    d
    #6   f                    
    #7   g <NA>               
    #8   h                    
    #9   i                    
    #10  j <NA> <NA>          
    #11  k <NA>               
    #12  l                    
    #13  m                   
    

    【讨论】:

    • 感谢您的帮助。出于好奇,如果 ID 列没有任何缺失值,那么函数 df == '' 的第二部分是否必要?
    • @Corey 如果缺少值是指空值,则不需要df == ""。在这里我们使用它是因为我们希望将它们保留为空值,而不是用 NA 替换它们。
    猜你喜欢
    • 1970-01-01
    • 2015-01-21
    • 1970-01-01
    • 2020-05-18
    • 1970-01-01
    • 1970-01-01
    • 2020-08-13
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多