【问题标题】:Merging two factor/character columns into one column将两个因子/字符列合并为一列
【发布时间】:2015-09-30 20:05:27
【问题描述】:

我有以下由

构建的数据集
help <- data.frame(var1 = c("red", NA, NA, NA, "red", "orange"),
               var2 = c(NA, "lightred", "blue", "lightred", NA, NA))

    var1     var2
1    red     <NA>
2   <NA> lightred
3   <NA>     blue
4   <NA> lightred
5    red     <NA>
6 orange     <NA>

我一直在尝试创建一个新变量newvar,它只是将因子变量合并到一个新列中。我希望得到如下输出

    var1     var2   newvar
1    red     <NA>    red
2   <NA> lightred    lightred
3   <NA>     blue    blue
4   <NA> lightred    lightred
5    red     <NA>    red
6 orange     <NA>    orange

这是我基于这里其他线程的尝试

help$newvar = ifelse(help$var1 == "", help$var2, help$var1)

当变量是因子时,newvar 是数字,这是有道理的,但只有来自 var1 的变量才会移动到 newvar。当字符时,同样只有来自var1 的字符移动到newvar

我知道有人问过类似的问题,但答案似乎无法解决此问题。 Merge two factor columns in R

在 dplyr 中也有办法做到这一点吗?我会采取任何我能得到的解决方案,只是好奇。

【问题讨论】:

  • 我在您的var1 中没有看到任何空白,我看到了缺失值。使用is.na(help$var1) 而不是help$var1 == ""
  • 另一个选项apply(help, 1, na.omit)

标签: r dplyr tidy


【解决方案1】:

我在您的 var1 中没有看到任何空白,我看到了缺失值。使用is.na(help$var1) 而不是help$var1 == ""

您还需要转换为字符,因为您有不同级别的因素。

help$newvar = ifelse(is.na(help$var1), as.character(help$var2), as.character(help$var1))

当然你可以使用dplyr,你只是在创建一个列

help = mutate(help, newvar = ifelse(is.na(var1), as.character(var2), as.character(var1)))

在 SQL 中,此操作称为 coalesce。您可能对How to implement coalesce efficiently in R 感兴趣

【讨论】:

  • 好的,很好。我明白你对 is.na 的意思......当我为示例构建这个 df 时,我把 "" 和 NA 都弄乱了。当我将其作为一个因素时,该代码为我提供了 newvar 的数字,当我转换为字符时,它运行良好
  • 也感谢您提供有关合并的资源
  • 谢谢,在字符转换中编辑。这里真正的教训是空白与缺失值不同。
  • 合并答案早于tidyr,但tidyr::unite 的另一个答案可能更方便。
  • 为什么你不能只使用基础 R 中的 transform 而不是 dplyr::mutate?语法完全一样
【解决方案2】:

如果你想使用 tidyr:

library(tidyr)

help[] <- lapply(help, as.character)
help[is.na(help)] <- ''
unite(help, new, var1:var2, sep='', remove=F)

#       new   var1     var2
#1      red    red         
#2 lightred        lightred
#3     blue            blue
#4 lightred        lightred
#5      red    red         
#6   orange orange      

或者基地Rhack:

transform(help, new = gsub('NA','',do.call(paste0, help))

#    var1     var2      new
#1    red     <NA>      red
#2   <NA> lightred lightred
#3   <NA>     blue     blue
#4   <NA> lightred lightred
#5    red     <NA>      red
#6 orange     <NA>   orange   

【讨论】:

    【解决方案3】:

    这是从help 中取出非NAs 值的另一种方法

    t(help)[t(!is.na(help))]
    ## [1] "red"      "lightred" "blue"     "lightred" "red"      "orange"  
    

    t 中的需要是因为 R 中的子集是按列而不是按行完成的

    【讨论】:

      【解决方案4】:

      在这种情况下,sqldf 包可以派上用场,正如 Gregor 指出的那样,函数 coalesce:

       library(sqldf)
       help$newvar <- sqldf("select coalesce(var1, var2) newvar from help")
      

      输出:

          var1     var2   newvar
      1    red     <NA>      red
      2   <NA> lightred lightred
      3   <NA>     blue     blue
      4   <NA> lightred lightred
      5    red     <NA>      red
      6 orange     <NA>   orange
      

      【讨论】:

      • 或者help &lt;- sqldf("select *, coalesce(var1, var2) newvar from help")
      • @G.Grothendieck 感谢您的有用评论
      猜你喜欢
      • 2014-11-08
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2017-06-14
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多