Angelika
Angelika

Reputation: 216

R optim: correct using for function with more than one argument

I am writing a function for minimization using optim. The task is to solve some similar optimization tasks in loop.

# K and k are always the same (they are read from a file)

K <- matrix(data = c(1, 2, 1, 2, 1, 
                 2, 16, 2, 1, 2, 
                 1, 2, 8, 2, 1,
                 2, 1, 2, 16, 2,
                 1, 2, 1, 2, 32),
        nrow = 5, ncol = 5, byrow = TRUE)

k <- c(-2, 4, 12, 0, 2)

# j will be changed

minimize <- function(beta){ #function to minimize (for beta)
value <- (1/2)*(t(beta)%*%K%*%beta) - t(k)%*%beta + j*abs(sum(beta)-n_s)
return(value)
}

myfunc <- function(K, k, m) #K is matrix, k is vector
{
   j_values <- 10^seq(-5, 5, length = m)
   for (i in 1:m)
   {
     current_j_value <- j_values[i]
     #I want to set j in minimize function as current_j_value (and also my k and K from file)
     # and then minimize it
     myans <- optim(c(0, 0, 0, 0, 0), minimize) # using minimize(K, k, j) doesn't work
     print(myans$par)
   }
}

myfunc(K, k, 5)

My question is how to give arguments to my minimize function (to create it dynamically?) and then use it in optim.

Upvotes: 0

Views: 326

Answers (1)

Croote
Croote

Reputation: 1424

If youw ant to include extra parameters in you minimize function you can add these in the optim call as from the documentation see ?optim the dots (...) ... Further arguments to be passed to fn and gr.

So including j, k, K and n_s in minimize

minimize <- function(beta, j, k, K, n_s){ #function to minimize (for beta)
  value <- (1/2)*(t(beta)%*%K%*%beta) - t(k)%*%beta + j*abs(sum(beta)-n_s)
  return(value)
}

and then adding these to the optim call (I have set n_s = 0) like,

myfunc <- function(K, k, m) #K is matrix, k is vector
{
  j_values <- 10^seq(-5, 5, length = m)
  for (i in 1:m)
  {
    current_j_value <- j_values[i]
    #I want to set j in minimize function as current_j_value (and also my k and K from file)
    # and then minimize it
    myans <- optim(c(0, 0, 0, 0, 0), minimize, j = current_j_value, k = k, K = K, n_s = 0) # using minimize(K, k, j) doesn't work
    print(myans$par)
  }
}

Running this then,

> myfunc(K, k, 5)
[1] -6.7956860  0.7999990  1.9999999  0.5333326  0.1290324
[1] -6.7911329  0.7996483  2.0000002  0.5329818  0.1290322
[1] -5.3512894  0.6889257  1.9999436  0.4222287  0.1290095
[1] -2.80295781  0.61426579  1.95348934  0.24715200 -0.01194974
[1] -1.2999142  0.4313710  1.3088572 -0.5764644  0.1361504

All the code together

# K and k are always the same (they are read from a file)

K <- matrix(data = c(1, 2, 1, 2, 1, 
                     2, 16, 2, 1, 2, 
                     1, 2, 8, 2, 1,
                     2, 1, 2, 16, 2,
                     1, 2, 1, 2, 32),
            nrow = 5, ncol = 5, byrow = TRUE)

k <- c(-2, 4, 12, 0, 2)

# j will be changed

minimize <- function(beta, j, k, K, n_s){ #function to minimize (for beta)
  value <- (1/2)*(t(beta)%*%K%*%beta) - t(k)%*%beta + j*abs(sum(beta)-n_s)
  return(value)
}

myfunc <- function(K, k, m) #K is matrix, k is vector
{
  j_values <- 10^seq(-5, 5, length = m)
  for (i in 1:m)
  {
    current_j_value <- j_values[i]
    #I want to set j in minimize function as current_j_value (and also my k and K from file)
    # and then minimize it
    myans <- optim(c(0, 0, 0, 0, 0), minimize, j = current_j_value, k = k, K = K, n_s = 0) # using minimize(K, k, j) doesn't work
    print(myans$par)
  }
}

myfunc(K, k, 5)

Upvotes: 1

Related Questions