# NOT RUN {
S <- createS(n = 3, p = 4)
tgt <- diag(4)
rags2ridges:::.armaRidgeP(S, tgt, 1.2)
rags2ridges:::.armaRidgePAnyTarget(S, tgt, 1.2)
rags2ridges:::.armaRidgePScalarTarget(S, 1, 1.2)
################################################################################
# The C++ estimators essentially amount to the following functions.
################################################################################
rev_eig <- function(evalues, evectors) { # "Reverse" eigen decomposition
evectors %*% diag(evalues) %*% t(evectors)
}
# R implementations
# As armaRidgePScalarTarget Inv
rRidgePScalarTarget <- function(S, a, l, invert = 2) {
ED <- eigen(S, symmetric = TRUE)
eigvals <- 0.5*(ED$values - l*a)
sqroot <- sqrt(l + eigvals^2)
if (l > 1e6 && (any(!is.finite(eigvals)) || any(!is.finite(sqroot)))) {
return(diag(a, nrow(S)))
}
D_inv <- 1.0/(sqroot + eigvals)
D_noinv <- (sqroot - eigvals)/l
if (invert == 2) { # Determine to invert or not
if (l > 1) { # Generally, use inversion for "small" lambda
invert = 0;
} else {
invert <- ifelse(any(!is.finite(D_inv)), 0, 1)
}
}
if (invert) {
eigvals <- D_inv
} else {
eigvals <- D_noinv
}
return(rev_eig(eigvals, ED$vectors))
}
# As armaRidgePAnyTarget
rRidgePAnyTarget <- function(S, tgt, l, invert = 2) {
ED <- eigen(S - l*tgt, symmetric = TRUE)
eigvals <- 0.5*ED$values
sqroot <- sqrt(l + eigvals^2)
if (l > 1e6 && (any(!is.finite(eigvals)) || any(!is.finite(sqroot)))) {
return(tgt)
}
D_inv <- 1.0/(sqroot + eigvals)
D_noinv <- (sqroot - eigvals)/l
if (invert == 2) { # Determine to invert or not
if (l > 1) { # Generally, use inversion for "small" lambda
invert = 0;
} else {
invert <- ifelse(any(!is.finite(D_inv)), 0, 1)
}
}
if (invert == 1) {
eigvals <- D_inv
} else {
eigvals <- D_noinv
}
return(rev_eig(eigvals, ED$vectors))
}
rRidgeP <- function(S, tgt, l, invert = 2) {
if (l == Inf) {
return(tgt)
}
a <- tgt[1,1]
if (tgt == diag(a, nrow(tgt))) {
rRidgePScalarTarget(S, tgt, l, invert)
} else {
rRidgePAnyTarget(S, tgt, l, invert)
}
}
# Contrasted to the straight forward implementations:
sqrtm <- function(X) { # Matrix square root
ed <- eigen(X, symmetric = TRUE)
rev_eig(sqrt(ed$values), ed$vectors)
}
# Straight forward (Lemma 1)
ridgeP1 <- function(S, tgt, l) {
solve(sqrtm( l*diag(nrow(S)) + 0.25*crossprod(S - l*tgt) ) + 0.5*(S - l*tgt))
}
# Straight forward (Lemma 1 + remark 6 + 7)
ridgeP2 <- function(S, tgt, l) {
1.0/l*(sqrtm(l*diag(nrow(S)) + 0.25*crossprod(S - l*tgt)) - 0.5*(S - l*tgt))
}
set.seed(1)
n <- 3
p <- 6
S <- covML(matrix(rnorm(p*n), n, p))
a <- 2.2
tgt <- diag(a, p)
l <- 1.21
(A <- ridgeP1(S, tgt, l))
(B <- ridgeP2(S, tgt, l))
(C <- rags2ridges:::.armaRidgePAnyTarget(S, tgt, l))
(CR <- rRidgePAnyTarget(S, tgt, l))
(D <- rags2ridges:::.armaRidgePScalarTarget(S, a, l))
(DR <- rRidgePScalarTarget(S, a, l))
(E <- rags2ridges:::.armaRidgeP(S, tgt, l))
# Check
equal <- function(x, y) {isTRUE(all.equal(x, y))}
stopifnot(equal(A, B) & equal(A, C) & equal(A, D) & equal(A, E))
stopifnot(equal(C, CR) & equal(D, DR))
# }
Run the code above in your browser using DataLab