【问题标题】:Replace numeric columns of dataset from other dataset从其他数据集中替换数据集的数字列
【发布时间】:2020-06-07 11:43:47
【问题描述】:

我想将一个数据集的数字列替换为相应转换数据集的数字列。我该怎么做(不使用特定于特定数据集的代码)?

例如来自库ggplot2mpg 的玩具示例:

mpg0 <- mpg

set.seed(123)
mpg0[sample(nrow(mpg),70,replace=FALSE),3] <- NA
mpg0[sample(nrow(mpg),70,replace=FALSE),8] <- NA
mpg0[sample(nrow(mpg),70,replace=FALSE),9] <- NA

sampled <- sample(nrow(mpg),50,replace=FALSE)
mpg_test <- mpg0[sampled,]
mpg_train <- mpg0[-sampled,]

mpg_mean <- mpg_train %>% group_by(cyl) %>% summarise_if(is.numeric,mean,na.rm=TRUE)
temp1 <- mpg_test %>% left_join(mpg_mean, by = 'cyl')

现在我想将mpg_test 的数字列(列displctyhwy--其他数字列中没有 NA)中的缺失值替换为左连接的相应列。我可以做到这一点

temp1 <- as.data.frame(temp1)
temp1[c(3,8,9)][is.na(temp1[c(3,8,9)])] <- temp1[c(12,14,15)][is.na(temp[c(3,8,9)])] 

但这是特定于该数据集的。 mutate_if 的问题是我不知道要放入什么函数。有没有一种很好的通用方法可以做到这一点,即改变数字列以获得平均值,将 NA 替换为对应左侧的同一行中的值- 加入列?

(请仅使用 dplyr)

【问题讨论】:

    标签: r dplyr


    【解决方案1】:

    您可以通过更改左连接并使用case_when 来做到这一点:

    library(dplyr)
    
    temp1 <- left_join(mpg_test, mpg_mean, by = "cyl")
    
    temp1 %>% 
      mutate_if(is.integer, as.numeric) %>% 
      mutate(displ.x =
               case_when(
                 is.na(displ.x) ~ displ.y,
                 TRUE ~ displ.x
               ),
             cty.x =
               case_when(
                 is.na(cty.x) ~ cty.y,
                 TRUE ~ cty.x
               ),
             hwy.x =
               case_when(
                 is.na(hwy.x) ~ hwy.y,
                 TRUE ~ hwy.x
               )) %>% 
      select(-c(displ.y, year.y, cty.y, hwy.y)) %>% 
      rename(displ = displ.x,
             year = year.x,
             cty = cty.x,
             hwy = hwy.x)
    

    【讨论】:

    • 查看我更新的帖子。 temp1[c(3,8,9)][is.na(temp1[c(3,8,9)])] &lt;- temp1[c(12,14,15)][is.na(temp1[c(3,8,9)])] 工作并且比这个解决方案更简单。我正在寻找一种不指定列的方法(只取所有数字列)
    【解决方案2】:

    你可以使用coalesce

    library(dplyr)
    
    mpg_test %>% 
      left_join(mpg_mean, by = 'cyl') %>%
      mutate(displ = coalesce(displ.x, displ.y), 
             cty = coalesce(displ.x, displ.y), 
             hwy = coalesce(hwy.x, hwy.y)) %>%
      select(-matches('\\.x|\\.y'))
    

    【讨论】:

    • 查看我更新的帖子。 temp1[c(3,8,9)][is.na(temp1[c(3,8,9)])] &lt;- temp1[c(12,14,15)][is.na(temp1[c(3,8,9)])] 工作并且比这个解决方案更简单。我正在寻找一种不指定列的方法(只取所有数字列)
    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2018-09-14
    相关资源
    最近更新 更多