目前,我有兩個非常相似的包裝器table和xtabs:
mytable <- function(..., useNA = "ifany") {
tab <- table(..., useNA = useNA)
# additional manipulations
tab
}
mytable(warpbreaks[-1])
myxtabs <- function(..., na.action = NULL, addNA = TRUE) {
tab <- xtabs(..., na.action = na.action, addNA = addNA)
# same manipulations as in mytable
tab
}
myxtabs(breaks ~ ., warpbreaks)
由于大多數代碼是重復的,我希望將兩個包裝器合并為一個。一個簡單的解決方案是:
newfun <- function(..., fun) {
fun <- match.fun(fun)
tab <- fun(...)
# same manipulations as in mytable
tab
}
newfun(warpbreaks[-1], fun = table)
newfun(breaks ~ ., warpbreaks, fun = xtabs)
但是,我可以根據匹配的函式指定默認引數嗎?IE:
- 如果
fun = table,設定useNA = "ifany"; - 或者如果
fun = xtabs,設定na.action = NULL和addNA = TRUE。
另外,什么是“推薦”的方式來限制fun只table和xtabs?我想我有很多方法可以實作這一點(stopifnot, if/ else, switch, match.arg),但我在這里尋找好的做法。
uj5u.com熱心網友回復:
1)嘗試在 newfun 中重新定義 table 和 xtabs。通過將本地版本轉換為字符并使用 do.call,確保 fun 正在呼叫本地版本。
newfun <- function(..., fun) {
table <- function(x, ..., useNA = "ifany") base::table(x, ..., useNA = useNA)
xtabs <- function(x, ..., na.action = NULL, addNA = NULL)
stats::xtabs(x, ..., na.action = na.action, addNA = addNA)
fun <- deparse(substitute(fun))
do.call(fun, list(...))
}
newfun(warpbreaks[-1], fun = table)
newfun(breaks ~ ., warpbreaks, fun = xtabs)
2)另一種方法是有 3 個函式,一個用于您的表版本,一個用于您的 xtabs 版本,然后一個包含其他每個人都會呼叫的公共代碼。這可能比(1)更直接。
mytable <- function(..., useNA = "ifany") {
tab <- table(..., useNA = useNA)
other(tab)
tab
}
myxtabs <- function(..., na.action = NULL, addNA = TRUE) {
tab <- xtabs(..., na.action = na.action, addNA = addNA)
other(tab)
tab
}
other <- function(x) {
# code
}
轉載請註明出處,本文鏈接:https://www.uj5u.com/qita/365874.html
下一篇:R:正確呼叫包含`i`的變數
