使用dplyr mutate()在R中根据存储为向量的列索引将data.frame字符列连接起来?

3

能否根据存储为向量的列索引连接数据框列,可能使用stringr函数(例如str_c())或paste?然后,如何使用dplyr mutate()创建新变量?

我想在电子邮件聚合任务中这样做,这意味着读取包含不同名称列(例如仅一个名称列和有时是名字和姓氏)的Excel工作表,使用readxl包。

例如:假设我想要连接包含"color"的所有列名在安装了tidyverse R包的starwars数据框中。

 library(tidyverse)
 colnames(starwars)
 [1] "name"       "height"     "mass"       "hair_color" "skin_color" "eye_color"  "birth_year" "gender"     "homeworld"  "species"    "films"     
 [12] "vehicles"   "starships" 

我可以使用以下代码捕获这些列的索引:

color_vec_num <- which(grepl("COLOR", toupper(colnames(starwars))))
print(color_vec_num)
[1] 4 5 6

什么是列名?
colnames(starwars)[color_vec_num]
[1] "hair_color" "skin_color" "eye_color"

我可以轻松地按名称将这些列名链接在一起。看着starwars的前4行:
str_c(starwars$hair_color, starwars$skin_color, starwars$eye_color)[1:4]
[1] "blondfairblue"   NA                NA                "nonewhiteyellow"

然而,我尝试使用列索引的方法失败了。
根据Akrun发现的笔误进行编辑,借鉴SO use of double brackets的方法可以创建(变异)一个新的变量,但这种方法单独且明确地识别每个列,而不是使用数字向量来识别每个列索引。
starwars %>% mutate(newcolor = paste(.[[4]],.[[5]], .[[6]])) %>% select(name, newcolor)
# A tibble: 87 x 2
   name               newcolor                    
   <chr>              <chr>                       
 1 Luke Skywalker     blond fair blue             
 2 C-3PO              NA gold yellow              
 3 R2-D2              NA white, blue red   

这种尝试让人想起了之前为不同问题提供的SO答案, 显然看起来不太对劲。

paste(starwars %>% select(color_vec_num), collapse = " ", stringsAsFactors = FALSE)
[1] "c(\"blond\", NA, NA, \"none\", \"brown\", \"brown, grey\", \"brown\", NA, \"black\", \"auburn, white\", \"blond\", \"auburn, grey\", \"brown\", \"brown\", NA, NA,
1个回答

2

我们可以使用列索引(.[color_vec_num])对列进行子集化,并在 mutate 中通过连接(str_c)将其缩减为单个列/向量。

library(tidyverse)
out <- starwars %>%
           mutate(newcolor = reduce(.[color_vec_num], str_c))
out %>% 
   pull(newcolor) %>% 
   head(4)
#[1] "blondfairblue"   NA                NA                "nonewhiteyellow"

关于OP的代码中出现的错误

paste(.[[4]],.[[5]], [[6]]

最后一个缺少 . ,即应该是:
starwars %>%
   mutate(newcolor = paste(.[[4]],.[[5]], .[[6]]))

话虽如此,与使用pastetidyr中的unite相比,使用str_c具有明显的优势,特别是在处理缺失值时。对于str_c,任何列中的缺失值都会返回整行的NA,而pasteunite会将NA转换为字符并返回类似于以下内容:

"NA gold yellow" 

对于第二个元素而言,如果其为NA,对于str_c则是不适用的。

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接