Reputation: 31
I am trying to fit a multivariate t distribution to CRSPday data in R. But optimization fails with non-finite finite-difference value [11] error every time. Can someone please suggest what am i doing wrong.
Basically i am passing mean, variance/correlation and DF as parameters and optimizing it.
I tried few hacks: changing bounds etc, using BFGS but nothing is working
Code Snippet:
mtfit <- function(series){
loglik <- function(par) {
mean <- par[1:4]
rho12 <- par[5]; rho13 <- par[6]; rho14 <- par[7]
rho23 <- par[8]; rho24 <- par[9]; rho34 <- par[10]
var1 <- par[11]; var2 <- par[12]; var3 <- par[13]; var4 <- par[14]
nu <- par[15]
cov12 <- rho12*sqrt(var1*var2); cov13 <- rho13*sqrt(var1*var3); cov14 <-
rho14*sqrt(var1*var4)
cov23 <- rho23*sqrt(var2*var3); cov24 <- rho24*sqrt(var2*var4); cov34 <-
rho34*sqrt(var3*var4)
covar <-matrix(c(var1,cov12,cov13,cov14,cov12,var2,cov23,cov24,cov13,cov23,var3,cov34,
cov14,cov24,cov34,var4),4,4)
f <- -sum(log(dmvt(x=series, delta=mean, sigma=covar, df=nu, log=FALSE)))
f
}
cov1 <- c(1e-2,1e-2,1e-2,1e-2,1e-2,1e-2,1e-10,1e-10,1e-10,1e-10)
cov2 <- c(0.99,0.99,0.99,0.99,0.99,0.99,1e-3,1e-3,1e-3,1e-3)
lower <- append(append(c(-1,-1,-1,-1),cov1),2.1)
upper <- append(append(c(0.01,0.001,0.001,0.001),cov2),7)
start <- lower
results <- optim(start, loglik, method = "L-BFGS-
B",lower=lower,upper=upper,hessian=T)
return(results)
}
fit_mine <- mtfit(CRSPday[,c(4:7)])
Upvotes: 2
Views: 131
Reputation: 31
Found a solution to this, hence sharing. Basically use cholesky decomposition instead of correlation to represent the co-variance matrix. In this case the bounds don't cause gradient error.
mtfit <- function(series){
loglik <- function(par) {
mean <- par[1:4]
A <-
matrix(c(par[5],par[6],par[7],par[8],0,par[9],par[10],par[11],0,0,par[12],
par[13],0,0,0,par[14]),nrow=4,byrow=T)
covar <- t(A)%*%A
f <- -sum(log(dmvt(x=series, delta=mean, sigma=covar, df=nu, log=FALSE)))
f
}
A <- chol(cov(series))
cov1 <- c(-.1,-.1,-.1,-.1,-.1,-.1,-.1,-.1,-.1,-.1)
cov2 <- c(.1,.1,.1,.1,.1,.1,.1,.1,.1,.1)
lower <- append(append(c(-0.02,-0.02,-0.02,-0.02),cov1),2.1)
upper <- append(append(c(0.02,0.02,0.02,0.02),cov2),15)
start <-
as.vector(c(apply(series,2,mean),A[1,1],A[1,2],A[1,3],A[1,4],A[2,2],
A[2,3],A[2,4],A[3,3],A[3,4],A[4,4],4))
results <- optim(start, loglik, method = "L-BFGS-B",lower=lower,
upper=upper,hessian=T)
return(results)
}
fit_mine <- mtfit(CRSPday[,c(4:7)])
Upvotes: 1