Как бороться с многоточием (...) при наличии необязательных аргументов?

У меня проблема с многоточием, когда я использую необязательные аргументы в своем определении функции. Чтобы уточнить, я определяю следующие функции:

func1 <- function (x) (x-2)^2

func3 <- function (fun, arg.curve.user){
  arg.curve.user$expr <-  substitute(func1)
  arg.curve.default <- list(col = "blue", n = 1000, main = "This is a test")
  arg.curve <- modifyList (arg.curve.default, arg.curve.user)
  do.call("curve", arg.curve)
}

# optimizes func1 and call func2 to plot func1
func2 <- function (lb, ub, n.restarts = 5, n.sim = 10, ...){
  arg.curve.user <- as.list(substitute(list(...)))
  output <- gosolnp(fun = func1, LB = lb, UB = ub,  n.restarts =  n.restarts, 
  n.sim =  n.sim)$par
  func3(fun = func1, arg.curve.user = arg.curve.user)
   return(output)
}

Вызывая func2, func1 оптимизируется, а также отображается через вызов func3 (требуется пакет Rsolnp).

func2 ( lb = 0, ub = 8, n.restarts = 5, n.sim = 10, n = 200, from = 0, to = 8)

Но предположим, что пользователь ошибается n.restarts и пишет nrestarts:

func2 ( lb = 0, ub = 8, nrestarts = 5, n.sim = 10, n = 200, from = 0, to = 8)

В этом случае я ожидаю, что R реализует следующие планы по устранению отсутствия n.restarts:

  1. присваивает значение по умолчанию, то есть 5, n.restarts в качестве необязательного аргумента
  2. объявляет предупреждение в конце: "nrestarts" не является графическим параметром

Но этого не происходит, и R присваивает значение n (200) для n.restarts!!

Может кто-нибудь помочь мне решить эту проблему?

Большое спасибо

2 ответа

Решение

Это частичное совпадение n аргумент n.restarts когда один не предоставлен пользователем. Вместо этого, вопреки совету @Andrie (который, конечно, будет работать), существует механизм, который позволяет вам продолжать работу, как это делается с аргументом. n и аргумент n.restarts, Хитрость заключается в том, чтобы разместить аргументы, которые вы хотите сопоставить точно после ...,

func2 <- function (lb, ub, ..., n.restarts = 5, n.sim = 10){
  writeLines(paste("Value of `n.restarts` is", n.restarts))
  arg.curve.user <- as.list(substitute(list(...)))
  output <- gosolnp(fun = func1, LB = lb, UB = ub,  n.restarts =  n.restarts, 
                    n.sim =  n.sim)$par
  func3(fun = func1, arg.curve.user = arg.curve.user)
  output
}

При использовании это дает:

> func2 (lb = 0, ub = 8, n.restarts = 2, n.sim = 10, n = 200,
+        from = 0, to = 8)
Value of `n.restarts` is 2          <---- Here!

Iter: 1 fn: 6.926e-15    Pars:  2.00000
Iter: 2 fn: 2.501e-15    Pars:  2.00000
solnp--> Completed in 2 iterations

Iter: 1 fn: 8.336e-16    Pars:  2.00000
Iter: 2 fn: 8.336e-16    Pars:  2.00000
solnp--> Completed in 2 iterations
[1] 2
> func2 (lb = 0, ub = 8, nrestarts = 2, n.sim = 10, n = 200,
+        from = 0, to = 8)
Value of `n.restarts` is 5          <---- Here! Default

Iter: 1 fn: 2.83e-15     Pars:  2.00000
Iter: 2 fn: 2.5e-15  Pars:  2.00000
solnp--> Completed in 2 iterations

Iter: 1 fn: 2.037e-15    Pars:  2.00000
Iter: 2 fn: 2.037e-15    Pars:  2.00000
solnp--> Completed in 2 iterations

Iter: 1 fn: 1.087e-15    Pars:  2.00000
Iter: 2 fn: 1.087e-15    Pars:  2.00000
solnp--> Completed in 2 iterations

Iter: 1 fn: 8.558e-16    Pars:  2.00000
Iter: 2 fn: 8.558e-16    Pars:  2.00000
solnp--> Completed in 2 iterations

Iter: 1 fn: 7.147e-16    Pars:  2.00000
Iter: 2 fn: 7.147e-16    Pars:  2.00000
solnp--> Completed in 2 iterations
[1] 2
Warning messages:
1: In plot.window(...) : "nrestarts" is not a graphical parameter
2: In plot.xy(xy, type, ...) : "nrestarts" is not a graphical parameter
3: In axis(side = side, at = at, labels = labels, ...) :
  "nrestarts" is not a graphical parameter
4: In axis(side = side, at = at, labels = labels, ...) :
  "nrestarts" is not a graphical parameter
5: In box(...) : "nrestarts" is not a graphical parameter
6: In title(...) : "nrestarts" is not a graphical parameter

Если вы придерживаетесь регулярной оценки аргументов, у вас больше шансов получить предупреждения. Опять же, вам не нужно использовать специальную оценку, чтобы получить поведение, которое вы хотите. Использование нестандартной оценки - плохая идея, поскольку вряд ли вы точно воспроизведете поведение R по умолчанию, что приведет к незначительным ошибкам для вас и ваших пользователей.

library(Rsolnp)

func1 <- function (x) (x-2)^2

func3 <- function (fun, col = "blue", n = 1000, main = "This is a test", ...){
  curve(func1, ..., n = n, col = col, main = main)
}

# optimizes func1 and call func2 to plot func1
func2 <- function (lb, ub, n.restarts = 5, n.sim = 10, ...){
  output <- gosolnp(fun = func1, LB = lb, UB = ub, n.restarts = n.restarts, 
  n.sim =  n.sim)$par
  func3(fun = func1, ...)
  return(output)
}

Затем, когда вы запускаете:

func2 ( lb = 0, ub = 8, nrestarts = 5, n.sim = 10, n = 200, from = 0, to = 8)

вы получаете предупреждения в соответствии с

Warning messages:
1: In plot.window(...) : "nrestarts" is not a graphical parameter
2: In plot.xy(xy, type, ...) : "nrestarts" is not a graphical parameter
3: In axis(side = side, at = at, labels = labels, ...) :
  "nrestarts" is not a graphical parameter
4: In axis(side = side, at = at, labels = labels, ...) :
  "nrestarts" is not a graphical parameter
5: In box(...) : "nrestarts" is not a graphical parameter
6: In title(...) : "nrestarts" is not a graphical parameter
Другие вопросы по тегам