当目标函数有一个时,如何编写一个能够遵循默认值的包装函数?

时间:2013-09-07 07:24:21

标签: r

我想写一个或多或少的通用调用者来保留其默认参数targetf

假设我们有一些第三方库targetf提供:

targetf<-function(x=1,...){
    print(paste("x =",x))
}

如何编写wrapperf,这将尊重targetf的默认参数,所以调用 wrapperf()不会产生错误消息Error in paste("x =", x) : argument "x" is missing, with no default

明显的候选人wrapperf1<-function(x,y) {targetf(x=x)}不起作用,但wrapperf1()失败。

wrapperf2<-function(...) {targetf(...)}行为正确,但它对我不起作用,因为我只关心传递x参数,(并可能将...保留给{中的其他函数{1}}身体)。

也许要解决这个问题,我必须使用省略号过滤,这对我来说是 terra incognita ......


关于如何解决问题的一个想法:也许我需要在wrapperf中从头开始创建一个特制的...对象来做这样的伪代码:

wrapperf

但我不知道如何开始将作业分配到省略号中......是否可能?我把这个问题分别放在SO:Is it possible to create an ellipsis () object from scratch


由于问题仍未解决,我决定将此问题发布到r-help@r-project.org

1 个答案:

答案 0 :(得分:1)

我会回复自己更详细的设置(我用targetf名称替换lib*)。 bar函数嵌套在foo个函数中,因此用户无法轻松看到它们的默认值。

libfoo<-function(par1=1,...)
{
    if (missing(par1))
    {
        warning("par1 is missing!!")
    }
    print(paste0('par1: ',par1))
    libbar(...)
}


libbar<-function(par2=1)
{
    if (missing(par2))
    {
        warning("par2 is missing!!")
    }
    print(paste0('par2: ',par2))
}


libfoo2<-function(par3=1,...)
{
    if (missing(par3))
    {
        warning("par3 is missing!!")
    }
    print(paste0('par3: ',par3))
    libbar2(...)
}

libbar2<-function(par4=1)
{
    if (missing(par4))
    {
        warning("par4 is missing!!")
    }
    print(paste0('par4: ',par4))
}

包装器:

wrapfun<-function(x,par1=3,...,par3,par4)
{
    libfoo(par1,...) #With dots everything is simple

    pars<-list()
    if(!missing(par3))
    {
        pars<-c(pars,par3=par3)
    }
    if(!missing(par4))
    {
        pars<-c(pars,par4=par4)
    }
    do.call(libfoo2,pars) #This is how we can pass specific arguments, and respecting missings properly.
}

这是一些输出:

wrapfun(par1=5,par2=5,par3=5,par4=5)
# [1] "par1: 5"
# [1] "par2: 5"
# [1] "par3: 5"
# [1] "par4: 5"


wrapfun()
# [1] "par1: 3"
# [1] "par2: 1"
# [1] "par3: 1"
# [1] "par4: 1"
# Warning messages:
# 1: In libbar(...) : par2 is missing!!
# 2: In (function (par3 = 1, ...)  : par3 is missing!!
# 3: In libbar2(...) : par4 is missing!!

wrapfun(par4=5)
# [1] "par1: 3"
# [1] "par2: 1"
# [1] "par3: 1"
# [1] "par4: 5"
# Warning messages:
# 1: In libbar(...) : par2 is missing!!
# 2: In (function (par3 = 1, ...)  : par3 is missing!!