使用 reduce2 和 rlang 改变列

Mutating columns with reduce2 and rlang

我正在尝试以下操作:

library(tidyverse)
library(rlang)

df <- data.frame(a = 1:2)

reduce2(list(df, df, df), letters[2:3], ~ mutate(.x, !!(.y) := 2:3))
#> Error in local_error_context(dots = dots, .index = i, mask = mask): promise already under evaluation: recursive default argument reference or earlier problems?

我确实知道许多将列更改为数据框的方法,但我正在努力学习 rlang

预期输出:

  a b c
1 1 2 2
2 2 3 3

我相信您知道您可以 df[letters[2:3]] <- 2:3 实现相同的输出,但我认为这不是您要找的。

要使用 purrrrlang,您可以使用 -

library(dplyr)
library(purrr)

bind_cols(df, map_dfc(letters[2:3], ~df %>% transmute(!!.x := 2:3)))

#  a b c
#1 1 2 2
#2 2 3 3

另一种方式是 -

map(letters[2:3], ~df %>% mutate(!!.x := 2:3)) %>% reduce(inner_join, by = 'a')

我认为 reduce2 不是正确的函数,因为在第一次迭代后您实际上并没有使用数据框列表中的任何项目。传递给 reduce2 的函数采用三个参数 - 第一个是要减少的对象,第二个是 .x 中的下一个项目,第三个是 .y 中的下一个项目。

这意味着如果您愿意,您仍然可以使用 reduce2,方法是:

reduce2(.x = list(df, df, df), .y = letters[2:3], 
        .f = function(A, B, C) mutate(A, {{C}} := 2:3))
#>   a b c
#> 1 1 2 2
#> 2 2 3 3

但请注意,您没有在函数体中使用第二个参数。你可以用 reduce:

reduce(list(df, 'b', 'c'), ~ mutate(.x, !!.y := 2:3))

组合purrr::reduce()rlang的方法是:

library(dplyr)
library(purrr)

reduce(letters[2:3], ~ .x %>% mutate(!!.y := 2:3), .init = df)

#   a b c
# 1 1 2 2
# 2 2 3 3

诀窍是将 df 分配给参数 .init