如何向使用 tidy eval 框架创建的函数添加检查?
How do I add checks to a function created using tidy eval framework?
假设我使用 tidy eval 框架创建了一个函数 -
library(tidyverse)
library(rlang)
my_function <- function(data, var){
var_expr <- enquo(var)
data %>%
group_by(!!var_expr) %>%
summarise(count = n()) %>%
ungroup()
}
当我运行以下函数时,我得到下面的结果
my_function(mtcars, cyl)
# A tibble: 3 x 2
cyl count
<dbl> <int>
1 4 11
2 6 7
3 8 14
如何向该函数添加以下检查 -
- 检查
data
是否是数据帧。如果不是,return错误data should be a dataframe
- 检查
var
是否丢失。如果是 return 错误 var is missing
您可以进行如下修改。
- 为了检查我们的输入数据是否属于特定的 class 我们可以检查它的 class 属性,在这种情况下无论是数据框还是 tibble 它们都包含 class
data.frame
- 还有
missing
函数,它通常在很多函数内部使用来检查参数是否被赋值,以便它们生成一个值作为默认值。在你的情况下,我们可以终止函数的执行(你也可以检查 length
函数的源代码,了解它如何在 size
参数丢失时指定一个值)
- 您可以使用
base::stop
代替亲爱的@akrun 指定的 rlang::abort
library(rlang)
my_function <- function(data, var){
if(!"data.frame" %in% attr(data, "class")) {
abort("data should be a data frame")
}
if(missing(var)) {
abort("var is missing")
}
var_expr <- enquo(var)
data %>%
group_by(!!var_expr) %>%
summarise(count = n()) %>%
ungroup()
}
特别感谢 亲爱的 @27 ϕ 9 让我注意到这个宝贵的观点。我们还可以在 stopifnot
函数中自定义输出错误消息,这是检查输入参数的另一种方式:
my_function <- function(data, var){
stopifnot("The input data is not of class data frame" = "data.frame" %in% attr(data, "class") ,
"var is missing" = !missing(var))
var_expr <- enquo(var)
data %>%
group_by(!!var_expr) %>%
summarise(count = n()) %>%
ungroup()
}
特别感谢 亲爱的 @IceCreamToucan 提出了另一个选项,它使用 inherits
函数代替 attr
。如果输入数据在其 class 属性中不包含 data.frame
它 returns FALSE
:
my_function <- function(data, var){
if(!inherits(data, "data.frame")) {
stop("data is not of class data.frame")
}
if(missing(var)) {
stop("var is missing")
}
var_expr <- enquo(var)
data %>%
group_by(!!var_expr) %>%
summarise(count = n()) %>%
ungroup()
}
假设我使用 tidy eval 框架创建了一个函数 -
library(tidyverse)
library(rlang)
my_function <- function(data, var){
var_expr <- enquo(var)
data %>%
group_by(!!var_expr) %>%
summarise(count = n()) %>%
ungroup()
}
当我运行以下函数时,我得到下面的结果
my_function(mtcars, cyl)
# A tibble: 3 x 2
cyl count
<dbl> <int>
1 4 11
2 6 7
3 8 14
如何向该函数添加以下检查 -
- 检查
data
是否是数据帧。如果不是,return错误data should be a dataframe
- 检查
var
是否丢失。如果是 return 错误var is missing
您可以进行如下修改。
- 为了检查我们的输入数据是否属于特定的 class 我们可以检查它的 class 属性,在这种情况下无论是数据框还是 tibble 它们都包含 class
data.frame
- 还有
missing
函数,它通常在很多函数内部使用来检查参数是否被赋值,以便它们生成一个值作为默认值。在你的情况下,我们可以终止函数的执行(你也可以检查length
函数的源代码,了解它如何在size
参数丢失时指定一个值) - 您可以使用
base::stop
代替亲爱的@akrun 指定的
rlang::abort
library(rlang)
my_function <- function(data, var){
if(!"data.frame" %in% attr(data, "class")) {
abort("data should be a data frame")
}
if(missing(var)) {
abort("var is missing")
}
var_expr <- enquo(var)
data %>%
group_by(!!var_expr) %>%
summarise(count = n()) %>%
ungroup()
}
特别感谢 亲爱的 @27 ϕ 9 让我注意到这个宝贵的观点。我们还可以在 stopifnot
函数中自定义输出错误消息,这是检查输入参数的另一种方式:
my_function <- function(data, var){
stopifnot("The input data is not of class data frame" = "data.frame" %in% attr(data, "class") ,
"var is missing" = !missing(var))
var_expr <- enquo(var)
data %>%
group_by(!!var_expr) %>%
summarise(count = n()) %>%
ungroup()
}
特别感谢 亲爱的 @IceCreamToucan 提出了另一个选项,它使用 inherits
函数代替 attr
。如果输入数据在其 class 属性中不包含 data.frame
它 returns FALSE
:
my_function <- function(data, var){
if(!inherits(data, "data.frame")) {
stop("data is not of class data.frame")
}
if(missing(var)) {
stop("var is missing")
}
var_expr <- enquo(var)
data %>%
group_by(!!var_expr) %>%
summarise(count = n()) %>%
ungroup()
}