在我彻底破坏事物的过程中,请考虑:
gbar<-function(x,y,x,a) x+2*y-4*a
Error: repeated formal argument 'x' on line 1
Run Code Online (Sandbox Code Playgroud)
R 正确检查我定义的函数是否违法正式.
但如果我手动搞砸了:
ffoo<-function(x,y,a) x+2*y-4*a
formals(ffoo)<-c(x=7, formals(ffoo))
Run Code Online (Sandbox Code Playgroud)
然后我只会在某些情况下发现某些事情是无效的.
ffoo(3,4,5,6)将会正确执行(虽然可能没有给我我预期的答案),也将如此ffoo(y=3,a=2); 然后ffoo(x=5,y=3,a=2)会抛出关于模糊参数名称的错误.
那么:是否有任何base-R或高级实用程序包具有对formals现有函数进行"完整性"检查的功能?
编辑:
如果你只是想检查重复的参数,你可以这样做:
any(duplicated(names(formals(ffoo))))
# [1] TRUE
Run Code Online (Sandbox Code Playgroud)
正如哈德利在下面的第二条评论中提到的那样,dput()不能保证为您提供函数的良好/完整表示,因此可能有一些函数在我的原始答案中描述的方法(留在下面)失败。
原答案:
正如Andrie 指出的 C 代码中所暗示的那样,这显然是 R 在解析(而不是评估)对 的调用时执行的检查function()。这就是为什么您能够通过调用来规避检查formals<-,这就是为什么以下(例如)也可以避免被检查。在这两种情况下,都会修改/创建函数而不解析对function().
eval(call("function", formals(ffoo), body(ffoo)))
# function (x = 7, x, y, a)
# x + 2 * y - 4 * a
Run Code Online (Sandbox Code Playgroud)
R 的解析机制通常不会在用户可见的 R 函数中公开,因此我猜想没有现成的函数 R 函数来执行此检查。不过,您可以通过将函数定义转换为其字符表示形式,然后尝试自己重新解析它,来执行与 R 在获取表达式或在命令行中输入表达式时执行的完全相同的一组检查。
总体思路如下:
parse(text = capture.output(dput(ffoo)))
# Error in parse(text = capture.output(dput(ffoo))) :
# repeated formal argument 'x' on line 1
Run Code Online (Sandbox Code Playgroud)
要将检查包装为函数,请执行以下操作:
isParseableFunction <- function(x) {
tryCatch(is.function(x) &
is.expression(parse(text = capture.output(dput(x)))),
error = function(e) FALSE)
}
isParseableFunction(data.frame)
# [1] TRUE
isParseableFunction(mean)
# [1] TRUE
isParseableFunction(ffoo)
# [1] FALSE
isParseableFunction(99)
# [1] FALSE
Run Code Online (Sandbox Code Playgroud)