r - 编写自己的 tidyselect 函数

标签 r tidyselect r-recipes

我编写了一个使用 {tidyselect} 选择器(例如 contains()starts_with() 等)的 R 包。我想向包中添加一些更多的选择辅助函数,以根据某些属性选择变量。例如,选择所有数值变量或可能所有逻辑变量。

我已经查看了 {tidyselect} 基本代码。但我无法推测变量的注册是如何工作的,因此无法将其扩展为通过属性选择变量。

我做了一些搜索,看起来 {recipes} 包已经成功地实现了我正在寻找的其他帮助程序(例如 all_numeric()),但我正在努力编写扩展函数我。 https://github.com/tidymodels/recipes/blob/master/R/selections.R

归根结底,我相信,我不明白当变量注册到 tidyselect::scoped_vars() 函数时发生了什么。如果我在干净的环境中运行 tidyselect::scoped_vars(vars = names(mtcars)),我看不到任何更改。但是我可以在注册变量后在全局环境中使用 {tidyselect} 助手。

names(mtcars)
#>  [1] "mpg"  "cyl"  "disp" "hp"   "drat" "wt"   "qsec" "vs"   "am"   "gear"
#> [11] "carb"
tidyselect::scoped_vars(vars = names(mtcars))

# returns position of column 'mpg'
tidyselect::starts_with("mp")
#> 1

对于某些文档的任何提示或指导将不胜感激!谢谢!

最佳答案

当您调用 scoped_vars() 时,给定的变量名称会在当前函数调用期间保存在内部环境中:

(function() {
  print(tidyselect:::vars_env$selected)
  tidyselect::scoped_vars(names(mtcars))
  print(tidyselect:::vars_env$selected)
})()
#> NULL
#>  [1] "mpg"  "cyl"  "disp" "hp"   "drat" "wt"   "qsec" "vs"   "am"   "gear"
#> [11] "carb"

print(tidyselect:::vars_env$selected)
#> NULL

据我所知,这是 {tidyselect} 保留的关于变量的唯一信息;所以如果要根据属性来选择,就得自己维护属性信息。这也是 {recipes} 所做的,使用 cur_info_env environment .

粗略的实现看起来像这样:

type_env <- rlang::new_environment()

select_with_attributes <- function(.data, ...) {
  type_env$types <- purrr::map(.data, class)
  dplyr::select(.data, ...)
}

all_numeric <- function() {
  which(purrr::map_lgl(type_env$types, ~ any(.x %in% "numeric")))
}

head(select_with_attributes(iris, all_numeric()))
#>   Sepal.Length Sepal.Width Petal.Length Petal.Width
#> 1          5.1         3.5          1.4         0.2
#> 2          4.9         3.0          1.4         0.2
#> 3          4.7         3.2          1.3         0.2
#> 4          4.6         3.1          1.5         0.2
#> 5          5.0         3.6          1.4         0.2
#> 6          5.4         3.9          1.7         0.4

reprex package 创建于 2019-06-13 (v0.2.1)

关于r - 编写自己的 tidyselect 函数,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/56582164/

相关文章:

unit-testing - 在 R 中测试统计函数的指南?

r - 调用 tidyselect-using 函数时指定 dots 参数,无需指定前面的参数

正则表达式(使用 tidyr 收集多组列)

r - Tidymodels tune_grid : "Can' t subset columns that don't exist"when not using formula

r - predict.train 与使用配方对象进行预测

r - 找到一对列中的最大值/最小值

r - 在sparklyr (R+spark) 中提取列名称的简单命令

r - 使用 r 中的正则表达式将括号放在以逗号分隔的字符周围