[R] convergence=0 in optim and nlminb is real?

Adelchi Azzalini azzalini at stat.unipd.it
Mon Dec 16 16:09:46 CET 2013


It must be the case that this issue has already been rised before,
but I did not manage to find it in past posting. 

In some cases, optim() and nlminb() declare a successful convergence,
but the corresponding Hessian is not positive-definite.  A simplified
version of the original problem is given in the code which for
readability is placed below this text.  The example is built making use
of package 'sn', but this is only required to set-up the example: the
question is about the outcome of the optimizers. At the end of the run,
a certain point is declared to correspont to a minimum since
'convergence=0' is reported, but the eigenvalues of the (numerically
evaluated) Hessian matrix at that point are not all positive.

Any views on the cause of the problem? (i) the point does not
correspong to a real minimum, (ii) it does dive a minimum but the
Hessian matrix is wrong, (iii) the eigenvalues are not right. 
...and, in case, how to get the real solution. 


Adelchi Azzalini

#------------------
library(sn) # version 0.4-18
data(ais, package="sn")
attach(ais)
X <- cbind(1,Ht,Wt) 
y <- cbind(bmi, lbm)
dettach(ais)
negLogLik <- function(vdp, x, y)
{
  d <- ncol(y)
  p <- ncol(x)
  beta <- matrix(vdp[1:(d*p)], p, d)
  Omega <- matrix(0, d, d)
  Omega[lower.tri(Omega, TRUE)] <- vdp[(p*d+1):(p*d+d*(d+1)/2)]
  Omega <- Omega + t(Omega) - diag(diag(Omega), d)
  if(any(eigen(Omega)$values <= 0)) return(Inf)
  omega <- sqrt(diag(Omega))
  alpha <- vdp[(p*d+d*(d+1)/2+1):(p*d+d*(d+1)/2+d)]
  nu <- vdp[p*d+d*(d+1)/2+d+1]
  if(nu <= 0) return(Inf)
  logL <- sum(dmst(y, x %*% beta, Omega, alpha, nu, log=TRUE))
  return(-logL)
}
# run 1
vdp <-  c(44, 0, 0, -4, 0, 0, 0.05, -0.5, 35, 0.5, -20, 3.5)
opt <- optim(vdp, negLogLik, method="BFGS", hessian=TRUE, x=X, y=y)
opt$value
# [1] 625.3
opt$convergence
# [1] 0
eigen(opt$hessian)$values
# [1]  7.539e+07  1.523e+06 .... 5.684e-02 -4.516e-01
#---
# run 2
vdp <-  c(44.17,  -0.2441,  0.303, -3.620, 0.04044, 0.8906, 
         0.0487, -0.5072, 36.33, 0.4445, -20.87, 3.5)
opt <- optim(vdp, negLogLik, method="BFGS", hessian=TRUE, x=X, y=y)
opt$value
# [1] 599.7
opt$convergence
# [1] 0
eigen(opt$hessian)$values
# [1]  1.235e+08  ....  3.845e-02 -1.311e-03 -6.701e+02
#---
# run 3
vdp <-  c(44.17,  -0.2441,  0.303, -3.620, 0.04044, 0.8906, 
         0.0487, -0.5072, 36.33, 0.4445, -20.87, 3.5)
opt <- optim(vdp, negLogLik, method="SANN", hessian=TRUE, x=X, y=y)
opt$value
# [1] 599.8
opt$convergence
# [1] 0
eigen(opt$hessian)$values
# [1]  1.232e+08  ....    3.225e-02 -6.681e-02 -7.513e+02
#--
# run 4
vdp <-  c(44.17,  -0.2441,  0.303, -3.620, 0.04044, 0.8906, 
         0.0487, -0.5072, 36.33, 0.4445, -20.87, 3.5)
opt <- optim(vdp, negLogLik, method="Nelder", hessian=TRUE, x=X, y=y)
opt$value
# [1] 599.7
opt$convergence
# [1] 1
#--
# run 5
vdp <-  c(44.17,  -0.2441,  0.303, -3.620, 0.04044, 0.8906, 
         0.0487, -0.5072, 36.33, 0.4445, -20.87, 3.5)
opt <- optim(vdp, negLogLik, method="CG", hessian=TRUE, x=X, y=y)
opt$value
# [1] 599.7
opt$convergence
# [1] 0
eigen(opt$hessian)$values
# [1]  1.236e+08  3.026e+06  .... 3.801e-02 -2.348e-04 -7.344e+02

#--
# run 6
vdp <-  c(44.17,  -0.2441,  0.303, -3.620, 0.04044, 0.8906, 
         0.0487, -0.5072, 36.33, 0.4445, -20.87, 3.5)
opt <- nlminb(vdp, negLogLik, x=X, y=y)
opt$obj
# [1] 599.7
H <- optimHess(opt$par, negLogLik, x=X, y=y)
eigen(H)$values
# [1]  1.236e+08  3.041e+06 ... 4.090e-05 -7.176e+02
=============
            _                           
platform       x86_64-unknown-linux-gnu    
arch           x86_64                      
os             linux-gnu                   
system         x86_64, linux-gnu           
status                                     
major          3                           
minor          0.2                         
year           2013                        
month          09                          
day            25                          
svn rev        63987                       
language       R                           
version.string R version 3.0.2 (2013-09-25)
nickname       Frisbee Sailing



More information about the R-help mailing list