将参数从“...”参数赋予R中的右函数

时间:2016-06-22 06:58:43

标签: r arguments parameter-passing

我有一个函数来计算分类变量和连续变量的矩阵的相关性:

correlation <- function(matrix, ...) {
    xx <- do.call(rbind, lapply(colnames(mtrc), function(ex_i) {
        ty_i <- wtype(matrix, ex_i)
        yy <- sapply(colnames(mtrc), function(ex_j) {
            ty_j <- wtype(matrix, ex_j)

            if(ty_i == "numeric" & ty_j == "numeric") {
                cor(mtrc[ , c(ex_i, ex_j)], ...)[1, 2]
            } else if(ty_i == "factor" & ty_j == "factor") {
                cramersV(table(mtrc[ , c(ex_i, ex_j)]), ...)
            } else {
                fm <- paste(ex_i, "~", ex_j)
                if(ty_i == "factor") {
                    fm <- paste(ex_j, "~", ex_i)
                }
                fm <- lm(fm, data = mtrc[ , c(ex_i, ex_j)], ...)
                lm.beta(fm)
            }
        })
        names(yy) <- colnames(mtrc)
        yy
    }))
    rownames(xx) <- colnames(mtrc)
    xx
}

我的问题是如何正确地将论据...传递给corcramerVlm。由于如果用户为cor提供参数并且矩阵中存在分类变量,则这三个函数的参数名称不匹配,cramerVlm会引发错误(< em>未使用的参数...... )。

所以......我愿意接受任何解决方案或想法。

1 个答案:

答案 0 :(得分:2)

我没有意识到Richard Scriven在2014年提出了一个很好的问题:Split up `...` arguments and distribute to multiple functions,当我在下面做出回答时。所以是的,这是一个重复的问题。但我会在这里保留我的答案,因为它代表了我的想法(以及我的想法)。

原始回答

我认为通过为您的correlation功能提供更好的控制,这会更好:

correlation <- function(matrix, cor.opt = list(), cramersV.opt = list(), lm.opt = list()) {
    xx <- do.call(rbind, lapply(colnames(mtrc), function(ex_i) {
        ty_i <- wtype(matrix, ex_i)
        yy <- sapply(colnames(mtrc), function(ex_j) {
            ty_j <- wtype(matrix, ex_j)

            if(ty_i == "numeric" & ty_j == "numeric") {
                do.call("cor", c(list(x = mtrc[ , c(ex_i, ex_j)]), cor.opt))[1, 2]
            } else if(ty_i == "factor" & ty_j == "factor") {
                do.call("cramersV", c(list(x = table(mtrc[ , c(ex_i, ex_j)])), cramersV.opt))
            } else {
                fm <- paste(ex_i, "~", ex_j)
                if(ty_i == "factor") {
                    fm <- paste(ex_j, "~", ex_i)
                }
                fm <- do.call("lm", c(list(formula = fm, data = mtrc[ , c(ex_i, ex_j)]), lm.opt))
                lm.beta(fm)
            }
        })
        names(yy) <- colnames(mtrc)
        yy
    }))
    rownames(xx) <- colnames(mtrc)
    xx
}

您可以通过参数cor.optcramersV.optlm.opt传递针对不同函数的不同参数。然后,在您的函数correlation中,使用do.call()进行所有相关的函数调用。

<强>注释

我喜欢@Roland的想法。他选择使用...,同时根据不同功能的形式论证分割list(...)。另一方面,我已经要求您手动将这些参数指定到不同的列表中。最后,我们俩都要求您使用do.call()进行函数调用。

Roland的想法广泛适用,因为它更容易扩展到需要...的更多功能。