【问题标题】:Transform multiple columns the tidy way以整洁的方式转换多个列
【发布时间】:2018-03-20 08:25:37
【问题描述】:

我想知道是否有在管道中转换多个列的解决方案。

假设我们有一个包含三列的 tibble。 iq_preiq_post 必须在对数尺度上进行转换并保存到新列中。

library(tidyverse)
library(magrittr)

df <- tibble(
  iq_pre = rnorm(10, 100, 15),
  iq_post = rnorm(10, 100, 18),
  gender = rep(c("m", "f"), each = 5)
)

我知道我可以通过执行以 R 为基础得到结果

df[c("iq_pre_lg", "iq_post_lg")] <- log(df[c("iq_pre", "iq_post")])

或使用 lapply 遍历列。

我想出的唯一整洁的解决方案是像这样对每一列手动使用 mutate

df %<>% 
  mutate(iq_pre_lg = log(iq_pre),
         iq_post_lg = log(iq_post))

由于应该转换的列的名称以相同的字母开头,我也可以使用

df %<>% 
  mutate_at(vars(starts_with("iq")), funs(lg = log(.)))

但是,如果我想转换 20 个不同名称的列怎么办?有没有办法使用purrr::map 甚至tidyr::nest 以更优雅的方式解决这个问题?

【问题讨论】:

    标签: r tidyverse


    【解决方案1】:

    我们可以使用

    df %>%
         mutate_at(vars(matches("iq")), log)
    

    matches 的一个优点是它可以在一次调用中匹配多个模式。例如,如果我们需要将函数应用于以 (^) 以 'iq' 开头的列或 (|) 以 ($) 以 'oq' 结尾的列,则可以将其传递到单个 @987654326 @

    df %>%
      mutate_at(vars(matches('^iq|oq$'), log)
    

    如果列名完全不同并且n列有n模式,但如果列的位置仍然有顺序,则可以将列位置编号传递给vars .在当前示例中,“iq”列是第 1 列和第 2 列

    df %>% 
       mutate_at(1:2, log)
    

    同样的,如果 20 列占据第 20 个位置

    df %>%
       mutate_at(1:20, log)
    

    或者如果位置是 1 到 6、8 到 12、41:50

    df %>%
        mutate_at(vars(1:6, 8:12, 41:50), log)
    

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 2023-03-07
      • 1970-01-01
      • 2019-12-14
      • 2020-02-17
      • 2020-02-18
      • 2019-01-27
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多