Nothing
source(system.file(file.path('tests', 'testthat', 'AD_test_utils.R'), package = 'nimble'))
BMDopt <- nimbleOptions("buildModelDerivs")
nimbleOptions(enableDerivs = TRUE)
nimbleOptions(buildModelDerivs = TRUE)
nimbleOptions(useADcholAtomic = TRUE)
nimbleOptions(useADsolveAtomic = TRUE)
nimbleOptions(useADmatMultAtomic = TRUE)
nimbleOptions(useADmatInverseAtomic = TRUE)
RwarnLevel <- options('warn')$warn
options(warn = 1)
relTol <- eval(formals(test_ADModelCalculate)$relTol)
relTol[3] <- 1e-6
relTol[4] <- 1e-4
# Standalone test
test_that("basics of R calls to PDinverse_logdet and dmnormAD work", {
set.seed(1)
cov <- crossprod(matrix(rnorm(9), nrow=3))
PDild <- PDinverse_logdet(cov)
prec <- solve(cov)
expect_equal(PDild[1:9][upper.tri(prec, diag=TRUE)], prec[upper.tri(prec, diag=TRUE)])
expect_equal(PDild[10], determinant(cov, TRUE)$modulus[1])
mu <- c(.2, .3, .1)
x <- c(.1, .2, .3)
chol_cov <- chol(cov)
expect_equal(dmnorm_inv_ld(x, mu, mat = cov, inv_ld = PDild, prec_param=FALSE),
dmnorm_chol(x, mu, chol_cov, prec_param=FALSE))
expect_equal(dmnorm_inv_ld(x, mu, mat = cov, inv_ld = PDild, prec_param=FALSE, log=TRUE),
dmnorm_chol(x, mu, chol_cov, prec_param=FALSE, log=TRUE))
PDild2 <- PDinverse_logdet(prec)
expect_equal(PDild2[1:9][upper.tri(cov, diag=TRUE)], cov[upper.tri(cov, diag=TRUE)])
expect_equal(PDild2[10], determinant(prec, TRUE)$modulus[1])
chol_prec <- chol(prec)
expect_equal(dmnorm_inv_ld(x, mu, mat = prec, inv_ld = PDild2, prec_param=TRUE),
dmnorm_chol(x, mu, chol_prec, prec_param=TRUE))
expect_equal(dmnorm_inv_ld(x, mu, mat = prec, inv_ld = PDild2, prec_param=TRUE, log=TRUE),
dmnorm_chol(x, mu, chol_prec, prec_param=TRUE, log=TRUE))
})
# Test in a model with dmnormAD
set.seed(1)
n <- 3
locs <- cbind(runif(n),runif(n))
dd <- matrix(nrow = n, ncol = n)
for(i in 1:n) for(j in 1:n) dd[i,j] <- sqrt(sum((locs[i,]-locs[j,])^2))
code <- nimbleCode({
sigma ~ dunif(0, 20)
rho ~ dunif(0,3)
cov[1:3,1:3] <- sigma*sigma*exp(-dd[1:3,1:3]/rho)
inv_ld[1:10] <- PDinverse_logdet(cov[1:3, 1:3])
x[1:3] ~ dmnormAD(mean = mu[1:3], cov = cov[1:3, 1:3])
})
inits <- list(sigma = 0.8, rho = 1.2, mu = c(.2, .3, .1))
constants = list(dd=dd)
data = list(x = c(.1, .2, .3))
model <- nimbleModel(code, data = data, constants = constants, inits = inits, buildDerivs=TRUE)
relTolTmp <- relTol
relTolTmp[2] <- 1e-6
relTolTmp[3] <- 1e-2
relTolTmp[4] <- 1e-2
relTolTmp[5] <- 1e-13
test_ADModelCalculate(model, useParamTransform = TRUE, relTol = relTolTmp,
newConstantNodes = list(dd = dd*1.1, x=c(.15, .25, .35)),
newUpdateNodes = list(mu = c(.22, .32, .12)),
checkCompiledValuesIdentical = FALSE, check01vs012jacIdentical = FALSE,
checkDoubleUncHessian = TRUE,
useFasterRderivs = TRUE, verbose = FALSE, name = 'dmnormAD with inv_ld')
## Depending on the order in which the test above appears in the sequence of testing,
## we have seen the following crash:
# ============================================
# testing HMC/MAP-based scenario
# --------------------------------------------
# Testing initial wrt values with initial constantNodes
# Using wrt: sigma rho
# corrupted size vs. prev_size while consolidating
# Aborted
cov <- crossprod(matrix(rnorm(25), 5))
mu <- c(0.2,0.1,0.3,0.15,0.25)
x <- c(0.1,0.2,0.15,0.3,0.12)
PDinverse_logdet_test <- make_AD_test2(
op = list(
name = "PDinverse_logdet with prec_param FALSE: positive definite inverse and log determinant test",
opParam = list(name = "PDinverse_logdet"),
expr = quote({
pdl <- PDinverse_logdet(mat)
out <- pdl
}),
args = list(
mat = quote(double(2))
),
outputType = quote(double(1))
),
argTypes = c(mat='double(2)'),
wrt = c('mat'),
inputs = list(record = list(mat = cov),
test = list(mat = cov+0.1))
)
PDinverse_logdet_test_out <- test_AD2(PDinverse_logdet_test)
dmnormAD_test1 <- make_AD_test2(
op = list(
name = "dmnormAD test with cov input and log fixed",
opParam = list(name = "dmormAD test 1"),
expr = quote({
pld <- PDinverse_logdet(cov)
logProb <- dmnorm_inv_ld(x, mu, mat=cov, inv_ld=pld, prec_param=0, log=TRUE)
out <- logProb
}),
args = list(
x = quote(double(1)),
mu = quote(double(1)),
cov = quote(double(2))
),
outputType = quote(double(0))
),
argTypes = c(x='double(1)', mu='double(1)', cov='double(2)'),
wrt = c('x','mu','mat'),
inputs = list(record = list(cov = cov, mu=mu, x=x),
test = list(cov = cov+0.1, mu=mu-0.07, x=x+0.03))
)
dmnormAD_test1_out <- test_AD2(dmnormAD_test1)
dmnormAD_test1b <- make_AD_test2(
op = list(
name = "dmnormAD test with cov input and log dynamics",
opParam = list(name = "dmormAD test 1"),
expr = quote({
pld <- PDinverse_logdet(cov)
logProb <- dmnorm_inv_ld(x, mu, mat=cov, inv_ld=pld, prec_param=0, log=log)
out <- logProb
}),
args = list(
x = quote(double(1)),
mu = quote(double(1)),
cov = quote(double(2)),
log = quote(double(0))
),
outputType = quote(double(0))
),
argTypes = c(x='double(1)', mu='double(1)', cov='double(2)', log='double(0)'),
wrt = c('x','mu','mat'),
inputs = list(record = list(cov = cov, mu=mu, x=x, log=1),
test = list(cov = cov+0.1, mu=mu-0.07, x=x+0.03, log=0))
)
dmnormAD_test1b_out <- test_AD2(dmnormAD_test1b)
prec <- solve(cov)
dmnormAD_test2 <- make_AD_test2(
op = list(
name = "dmnormAD test with prec input and log fixed",
opParam = list(name = "dmormAD test 1"),
expr = quote({
pld <- PDinverse_logdet(prec)
logProb <- dmnorm_inv_ld(x, mu, mat=prec, inv_ld=pld, prec_param=1, log=TRUE)
out <- logProb
}),
args = list(
x = quote(double(1)),
mu = quote(double(1)),
prec = quote(double(2))
),
outputType = quote(double(0))
),
argTypes = c(x='double(1)', mu='double(1)', prec='double(2)'),
wrt = c('x','mu','mat'),
inputs = list(record = list(prec = prec, mu=mu, x=x),
test = list(prec = prec+0.1, mu=mu-0.07, x=x+0.03))
)
dmnormAD_test2_out <- test_AD2(dmnormAD_test2)
dmnormAD_test2b <- make_AD_test2(
op = list(
name = "dmnormAD test with prec input and log dynamic",
opParam = list(name = "dmormAD test 1"),
expr = quote({
pld <- PDinverse_logdet(prec)
logProb <- dmnorm_inv_ld(x, mu, mat=prec, inv_ld=pld, prec_param=1, log=log)
out <- logProb
}),
args = list(
x = quote(double(1)),
mu = quote(double(1)),
prec = quote(double(2)),
log = quote(double(0))
),
outputType = quote(double(0))
),
argTypes = c(x='double(1)', mu='double(1)', prec='double(2)', log='double(0)'),
wrt = c('x','mu','mat'),
inputs = list(record = list(prec = prec, mu=mu, x=x, log=0),
test = list(prec = prec+0.1, mu=mu-0.07, x=x+0.03, log=1))
)
dmnormAD_test2b_out <- test_AD2(dmnormAD_test2b)
## Check that rmnorm_inv_ld works and draws the same numbers as from rmnorm_chol
test_that("rmnorm_inv_ld works and matches rmnorm_chol", {
set.seed(1)
cov <- crossprod(matrix(rnorm(25), 5))
PDild_cov <- PDinverse_logdet(cov)
chol_cov <- chol(cov)
prec <- solve(cov)
PDild_prec <- PDinverse_logdet(prec)
chol_prec <- chol(prec)
mu <- c(0.2,0.1,0.3,0.15,0.25)
# PD_ild (PDinverse_logdet) will be ignored for method 2, rmnorm_chol
nf <- nimbleFunction(
run = function(mu=double(1), mat=double(2), PDild=double(1),
prec_param=double(0), method = integer(0)) {
if(method == 1)
ans <- rmnorm_inv_ld(1, mu, mat=mat, inv_ld = PDild, prec_param=prec_param)
if(method == 2)
ans <- rmnorm_chol(1, mu, cholesky = mat, prec_param=prec_param)
return(ans)
returnType(double(1))
}
)
cnf <- compileNimble(nf)
# uncompiled
set.seed(1); x_PLD_0 <- nf(mu, cov, PDild_cov, 0, 1)
set.seed(1); x_chol_0 <- nf(mu, chol_cov, c(0), 0, 2)
set.seed(1); x_PLD_1 <- nf(mu, prec, PDild_prec, 1, 1)
set.seed(1); x_chol_1 <- nf(mu, chol_prec, c(0), 1, 2)
# compiled
set.seed(1); Cx_PLD_0 <- cnf(mu, cov, PDild_cov, 0, 1)
set.seed(1); Cx_chol_0 <- cnf(mu, chol_cov, c(0), 0, 2)
set.seed(1); Cx_PLD_1 <- cnf(mu, prec, PDild_prec, 1, 1)
set.seed(1); Cx_chol_1 <- cnf(mu, chol_prec, c(0), 1, 2)
# look all together
#rbind(x_PLD_0, x_chol_0, x_PLD_1, x_chol_1,
# Cx_PLD_0, Cx_chol_0, Cx_PLD_1, Cx_chol_1)
expect_equal(x_PLD_0, x_chol_0)
expect_equal(x_PLD_1, x_chol_1)
expect_equal(Cx_PLD_0, Cx_chol_0)
expect_equal(Cx_PLD_1, Cx_chol_1)
expect_equal(x_PLD_0, Cx_PLD_0)
expect_equal(x_PLD_1, Cx_PLD_1)
# Check use of recycling rule for the mean
mu <- c(0, 100)
set.seed(1); x_PLD_0 <- nf(mu, cov, PDild_cov, 0, 1)
set.seed(1); x_chol_0 <- nf(mu, chol_cov, c(0), 0, 2)
set.seed(1); x_PLD_1 <- nf(mu, prec, PDild_prec, 1, 1)
set.seed(1); x_chol_1 <- nf(mu, chol_prec, c(0), 1, 2)
# compiled
set.seed(1); Cx_PLD_0 <- cnf(mu, cov, PDild_cov, 0, 1)
set.seed(1); Cx_chol_0 <- cnf(mu, chol_cov, c(0), 0, 2)
set.seed(1); Cx_PLD_1 <- cnf(mu, prec, PDild_prec, 1, 1)
set.seed(1); Cx_chol_1 <- cnf(mu, chol_prec, c(0), 1, 2)
expect_equal(x_PLD_0, x_chol_0)
expect_equal(x_PLD_1, x_chol_1)
expect_equal(Cx_PLD_0, Cx_chol_0)
expect_equal(Cx_PLD_1, Cx_chol_1)
expect_equal(x_PLD_0, Cx_PLD_0)
expect_equal(x_PLD_1, Cx_PLD_1)
mu <- c(0, 10, 20, 30, 40, 50, 60) # too long, only first 5 should be used
set.seed(1); x_PLD_0 <- nf(mu, cov, PDild_cov, 0, 1)
set.seed(1); x_chol_0 <- nf(mu, chol_cov, c(0), 0, 2)
set.seed(1); x_PLD_1 <- nf(mu, prec, PDild_prec, 1, 1)
set.seed(1); x_chol_1 <- nf(mu, chol_prec, c(0), 1, 2)
# compiled
set.seed(1); Cx_PLD_0 <- cnf(mu, cov, PDild_cov, 0, 1)
set.seed(1); Cx_chol_0 <- cnf(mu, chol_cov, c(0), 0, 2)
set.seed(1); Cx_PLD_1 <- cnf(mu, prec, PDild_prec, 1, 1)
set.seed(1); Cx_chol_1 <- cnf(mu, chol_prec, c(0), 1, 2)
expect_equal(x_PLD_0, x_chol_0)
expect_equal(x_PLD_1, x_chol_1)
expect_equal(Cx_PLD_0, Cx_chol_0)
expect_equal(Cx_PLD_1, Cx_chol_1)
expect_equal(x_PLD_0, Cx_PLD_0)
expect_equal(x_PLD_1, Cx_PLD_1)
})
test_that("non-assignment of dmnormAD if cholesky param used", {
code <- nimbleCode({
y[1:3] ~ dmnorm(mu[1:3], cholesky = L[1:3,1:3], prec_param = 0)
})
expect_message(m <- nimbleModel(code, inits=list(mu=rep(0,3),L=diag(3))),
"Detected use of `cholesky` parameterization")
})
test_that("lifting of PDinverse_logdet", {
code <- nimbleCode({
y[1:3] ~ dmnorm(mu[1:3], Q[2, 1:3, 5:7, 1])
})
m <- nimbleModel(code, data = list(y=rnorm(3)))
which_PDinverse <- grep("PDinverse_logdet", m$getNodeNames())
expect_identical(length(m[[m$getNodeNames()[which_PDinverse]]]), 10L)
})
# getParam
test_that('getParam', {
code = nimbleCode({
a[1:4] ~ dmnorm(mu[1:4],pr[1:4,1:4])
})
pr1 = diag(4)
pr1[1,2]=pr1[2,1]=.3
pr1[1,3]=pr1[3,1]=-.1
pr1[2,3]=pr1[3,2] = 0.4
pr2 <- pr1
pr1[1,2]=pr1[2,1]=.5
pr1[1,3]=pr1[3,1]=-.2
pr1[2,3]=pr1[3,2] = 0.3
m = nimbleModel(code, inits =list(mu=rep(1,4), pr = pr1))
cm = compileNimble(m)
cm$pr <- pr2
cm$calculate(cm$getDependencies('pr'))
expect_identical(pr1, m$getParam('a', 'prec'))
expect_identical(pr2, cm$getParam('a', 'prec'))
expect_equal(solve(pr1), m$getParam('a', 'cov'))
expect_equal(solve(pr2), cm$getParam('a', 'cov'))
code = nimbleCode({
a[1:3] ~ dmnorm(mu[1:3],cov=pr[1:3,1:3])
})
pr1 = diag(3)
pr1[1,2]=pr1[2,1]=.3
pr2 <- pr1
pr1[1,2]=pr1[2,1]=.5
m = nimbleModel(code, inits =list(mu=rep(1,3), pr = pr1))
cm = compileNimble(m)
cm$pr <- pr2
cm$calculate(cm$getDependencies('pr'))
expect_identical(pr1, m$getParam('a', 'cov'))
expect_identical(pr2, cm$getParam('a', 'cov'))
expect_equal(solve(pr1), m$getParam('a', 'prec'))
expect_equal(solve(pr2), cm$getParam('a', 'prec'))
})
# test-models
K <- 2
y <- c(.1, .3)
model <- function() {
y[1:K] ~ dmnorm(mu[1:K], prec[1:K,1:K]);
for(i in 1:K) {
mu0[i] <- 0
}
R[1,1] <- .01
R[2,2] <- .01
R[1,2] <- 0
R[2,1] <- 0
Omega[1,1] <- .01
Omega[2,2] <- .01
Omega[1,2] <- 0
Omega[2,1] <- 0
mu[1:K] ~ dmnorm(mu0[1:K], Omega[1:K,1:K])
prec[1:K,1:K] ~ dwish(R[1:K,1:K], 5)
}
inits <- list(mu = c(0,0), prec = matrix(c(.005,.001,.001,.005), 2))
data <- list(K = K, y = y)
testBUGSmodel(example = 'testN', dir = "",
model = model, data = data, inits = inits,
useInits = TRUE)
# Polya-gamma
test_that('polyagamma validity checks', {
## Various valid basic model structures
code <- nimbleCode({
for(i in 1:n) {
p0[i] <- expit(b0+b1*x[i])
y0[i] ~ dbern(p0[i])
logit(p1[i]) <- a0 + a1*x[i]
y1[i]~dbern(p1[i])
logit(p2[i]) <- inprod(x2[i,1:p], b2[1:p])
y2[i]~dbin(p2[i], size = m)
logit(p3[i]) <- x2[i,1:p] %*% b3[1:p]
y3[i]~dbin(p3[i], 1)
}
m ~ dpois(5)
b0~dnorm(0, sd=10)
b1~dnorm(0, sd=10)
a0~dnorm(0, sd=10)
a1~dnorm(0, sd=10)
b2[1:p] ~ dmnorm(mu[1:p], Q[1:p,1:p])
for(i in 1:p)
b3[i] ~ dnorm(0, sd = 10)
})
n <- 10
p <- 3
constants <- list(n=n, p=p, x = runif(n), x2 = matrix(runif(n*p),n))
ys <- rep(1,n)
data <- list(y0 = ys, y1 = ys, y2 = ys, y3 = ys)
m <- nimbleModel(code, constants = constants, data = data)
conf <- configureMCMC(m, nodes = 'm')
expect_silent(conf$addSampler(type='polyagamma', target=c('b0','b1')))
expect_silent(conf$addSampler(type='polyagamma', target=c('a0','a1')))
expect_silent(conf$addSampler(type='polyagamma', target=c('b2')))
expect_silent(conf$addSampler(type='polyagamma', target=c('b3')))
expect_silent(mcmc <- buildMCMC(conf))
## dnorm + dmnorm
code <- nimbleCode({
for(i in 1:n) {
p0[i] <- expit(b[1]+u[k[i]]+b[2]*x[i])
y0[i] ~ dbern(p0[i])
}
b[1:2] ~ dmnorm(z[1:2], pr[1:2,1:2])
for(i in 1:p)
u[i] ~ dnorm(0,1)
})
n <- 9
p <- 3
constants <- list(n=n, p=p, x = runif(n), k = rep(1:3, each = 3), z=rep(0,2), pr=diag(2))
ys <- rep(1,n)
data <- list(y0 = ys)
m <- nimbleModel(code, constants = constants, data = data)
conf <- configureMCMC(m, nodes = NULL)
expect_silent(conf$addSampler(type='polyagamma', target=c('b','u')))
expect_silent(mcmc <- buildMCMC(conf))
mcmc$run(1)
expect_equal(mcmc$samplerFunctions[[1]]$X,
cbind(rep(1,n), constants$x, c(rep(1,3),rep(0,6)),
c(rep(0,3),rep(1,3),rep(0,3)),
c(rep(0,6),rep(1,3))))
lens <- c(2,1,1,1); names(lens) <- c('b[1:2]','u[1]','u[2]','u[3]')
expect_equal(mcmc$samplerFunctions[[1]]$nodeLengths, lens)
})
test_that('Wishart-dmnorm conjugacy', {
n <- 3
R <- diag(rep(1,3))
mu <- 1:3
Y <- matrix(rnorm(9), 3)
data <- list(Y = Y, mu = mu, R = R)
code <- nimbleCode( {
for(i in 1:3) {
Y[i, 1:3] ~ dmnorm(mu[1:3], Omega[1:3,1:3]);
}
Omega[1:3,1:3] ~ dwish(R[1:3,1:3], 4);
})
m <- nimbleModel(code, data = data)
conf <- configureMCMC(m)
expect_identical(conf$getSamplers()[[1]]$name, "conjugate_dwish_dmnormAD_identity")
code <- nimbleCode( {
for(i in 1:3) {
Y[i, 1:3] ~ dmnorm(mu[1:3], cov = Omega[1:3,1:3]);
}
Omega[1:3,1:3] ~ dwish(R[1:3,1:3], 4);
})
m <- nimbleModel(code, data = data)
conf <- configureMCMC(m)
expect_identical(conf$getSamplers()[[1]]$name, "RW_wishart")
code <- nimbleCode( {
for(i in 1:3) {
Y[i, 1:3] ~ dmnorm(mu[1:3], Omega[1:3,1:3]);
}
Omega[1:3,1:3] ~ dinvwish(R[1:3,1:3], 4);
})
m <- nimbleModel(code, data = data)
conf <- configureMCMC(m)
expect_identical(conf$getSamplers()[[1]]$name, "RW_wishart")
code <- nimbleCode( {
for(i in 1:3) {
Y[i, 1:3] ~ dmnorm(mu[1:3], cov = Omega[1:3,1:3]);
}
Omega[1:3,1:3] ~ dinvwish(R[1:3,1:3], 4);
})
m <- nimbleModel(code, data = data)
conf <- configureMCMC(m)
expect_identical(conf$getSamplers()[[1]]$name, "conjugate_dinvwish_dmnormAD_identity")
})
# Run various NIMBLE tests that use dmnorm with dmnormAD instead.
# From test-mcmc.R
## verbose: set to FALSE
nimbleVerboseSetting <- nimbleOptions('verbose')
nimbleOptions(verbose = FALSE)
## MCMC progress bar: set to FALSE
nimbleProgressBarSetting <- nimbleOptions('MCMCprogressBar')
nimbleOptions(MCMCprogressBar = FALSE)
## MCMC orderSamplersPosteriorPredictiveLast - save current setting
nimbleReorderPPsamplersSetting <- getNimbleOption('MCMCorderPosteriorPredictiveSamplersLast')
## MCMC use usePosteriorPredictiveSampler - save current setting
nimbleUsePosteriorPredictiveSamplerSetting <- getNimbleOption('MCMCusePosteriorPredictiveSampler')
## MCMC calculation include predictive dependencies - save current setting
nimbleUsePredictiveDependenciesSetting <- nimbleOptions('MCMCusePredictiveDependenciesInCalculations')
## MCMC warn about unsampled nodes - save current setting
nimbleWarnUnsampledNodesSetting <- nimbleOptions('MCMCwarnUnsampledStochasticNodes')
test_that('elliptical slice sampler setup', {
set.seed(0)
ESScode <- quote({
x[1:d] ~ dmnorm(mu_x[1:d], prec = prec_x[1:d, 1:d])
y[1:d] ~ dmnorm(x[1:d], prec = prec_y[1:d, 1:d])
})
d <- 3
mu_x <- rnorm(d)
temp <- array(rnorm(d^2), c(d,d))
prec_x <- solve(temp %*% t(temp))
temp <- array(rnorm(d^2), c(d,d))
prec_y <- solve(temp %*% t(temp))
y <- rnorm(d)
ESSconstants <- list(d = d, mu_x = mu_x, prec_x = prec_x, prec_y = prec_y)
ESSdata <- list(y = y)
ESSinits <- list(x = rep(0, d))
test_mcmc(model = ESScode, data = c(ESSconstants, ESSdata), inits = ESSinits,
name = 'exact values of elliptical slice sampler',
seed = 0,
exactSample = list(`x[1]` = c(-0.492880566939352, -0.214539223107114, 1.79345037297218, 1.17324496091208, 2.14095077672555, 1.60417482445964, 1.94196916651627, 2.66737323347255, 2.66744178776022, 0.253966883192744), `x[2]` = c(-0.161210109217102, -0.0726534676226932, 0.338308532423757, -0.823652445515156, -0.344130712698579, -0.132642244861469, -0.0253168895009594, 0.0701624130921676, 0.0796842215444978, -0.66369112443311), `x[3]` = c(0.278627475932455, 0.0661336950029345, 0.407055002920732, 1.98761228946318, 1.0839897275519, 1.00262648370199, 0.459841485268785, 2.59229443025387, 1.83769567435409, 1.92954706515119)),
samplers = list(list(type = 'ess', target = 'x')))
test_mcmc(model = ESScode, data = c(ESSconstants, ESSdata), inits = ESSinits,
name = 'results to tolerance of elliptical slice sampler',
results = list(mean = list(x = c(1.0216463, -0.4007247, 1.1416904))),
resultsTolerance = list(mean = list(x = c(0.01, 0.01, 0.01))),
numItsC = 100000,
samplers = list(list(type = 'ess', target = 'x')), avoidNestedTest = TRUE)
})
test_that('block sampler on MVN node setup', {
code <- nimbleCode({
mu[1] <- 10
mu[2] <- 20
mu[3] <- 30
x[1:3] ~ dmnorm(mu[1:3], prec = Q[1:3,1:3])
})
Q = matrix(c(1.0,0.2,-1.0,0.2,4.04,1.6,-1.0,1.6,10.81), nrow=3)
data = list(Q = Q)
inits = list(x = c(10, 20, 30))
test_mcmc(model = code, name = 'block sampler on multivariate node', data = data, seed = 0, numItsC = 10000,
results = list(mean = list(x = c(10,20,30)),
var = list(x = diag(solve(Q)))),
resultsTolerance = list(mean = list(x = rep(1,3)),
var = list(x = c(.1, .03, .01))),
samplers = list(
list(type = 'RW_block', target = 'x[1:3]')), avoidNestedTest = TRUE)
# caution: setting targetNodes='x' works but the initial end sampler is not removed because x[1:3] in targetNode in default sampler != 'x' in targetNodes passed in
if(FALSE) {
Rmodel <- nimbleModel(code, constants = list(Q=Q))
mcmcspec <- MCMCspec(Rmodel, nodes = NULL)
mcmcspec$addSampler(type = 'RW_block', target = 'x', control = list(adaptInterval=500))
mcmcspec$getMonitors()
Rmcmc <- buildMCMC(mcmcspec)
Cmodel <- compileNimble(Rmodel)
Cmcmc <- compileNimble(Rmcmc, project = Rmodel)
Cmcmc(200000) ## this runs nearly instantaneously on my computer -DT
samples <- as.matrix(nfVar(Cmcmc, 'mvSamples'))
samples <- samples[50001:200000,]
dim(samples)
apply(samples, 2, mean)
solve(Q)
cov(samples)
propCov <- nfVar(Cmcmc, 'samplerFunctions')[[1]]$propCov
scale <- nfVar(Cmcmc, 'samplerFunctions')[[1]]$scale
propCov * scale^2
nfVar(Cmcmc, 'samplerFunctions')[[1]]$scaleHistory
nfVar(Cmcmc, 'samplerFunctions')[[1]]$acceptanceRateHistory
nfVar(Cmcmc, 'samplerFunctions')[[1]]$scale
nfVar(Cmcmc, 'samplerFunctions')[[1]]$propCov
## why is the proposal cov w/ .99 cross-corrs?
## also MCMC in C takes a surprisingly long time - this might be threaded lin alg behaving badly on small matrices
}
})
test_that('second block sampler on multivariate node', {
### DT's model
mu <- c(1,2,3)
corr <- matrix(c(1,.8,0.3,.8,1,0,0.3,0,1), nrow=3)
varr <- c(1,2,3)
Sig <- diag(sqrt(varr))
Q <- Sig %*% corr %*% Sig
P <- solve(Q)
code <- nimbleCode({
x[1:3] ~ dmnorm(mu[1:3], prec = P[1:3,1:3])
})
data = list(P = P, mu = mu)
test_mcmc(model = code, name = 'second block sampler on multivariate node', data = data, seed = 0, numItsC = 100000,
results = list(mean = list(x = mu),
var = list(x = varr)),
resultsTolerance = list(mean = list(x = rep(.1,3)),
var = list(x = c(.1,.1,.1))),
samplers = list(
list(type = 'RW_block', target = 'x[1:3]')), avoidNestedTest = TRUE)
})
test_that('MVN conjugate setup', {
### MVN conjugate update
set.seed(0)
mu0 = 1:3
Q0 = matrix(c(1, .2, .8, .2, 2, 1, .8, 1, 2), nrow = 3)
Q = solve(matrix(c(3, 1.7, .9, 1.7, 2, .6, .9, .6, 1), nrow = 3))
a = c(-2, .5, 1)
B = matrix(rnorm(9), 3)
##### not currently working - see Perry's email of ~ 10/6/14
## code <- nimbleCode({
## mu[1:3] ~ dmnorm(mu0[1:3], Q0[1:3, 1:3])
## y[1:3] ~ dmnorm(asCol(a[1:3]) + B[1:3, 1:3] %*% asCol(mu[1:3]), Q[1:3, 1:3])
## })
code <- nimbleCode({
mu[1:3] ~ dmnorm(mu0[1:3], Q0[1:3, 1:3])
y_mean[1:3] <- asCol(a[1:3]) + B[1:3, 1:3] %*% asCol(mu[1:3])
y[1:3] ~ dmnorm(y_mean[1:3], Q[1:3, 1:3])
})
mu <- mu0 + chol(solve(Q0)) %*% rnorm(3)
# make sure y is a vec not a 1-col matrix or get a dimensionality error
y <- c(a + B%*%mu + chol(solve(Q)) %*% rnorm(3))
data = list(mu0 = mu0, Q0 = Q0, Q = Q, a = a, B = B, y = y)
muQtrue = t(B) %*% Q%*%B + Q0
muMeanTrue = c(solve(muQtrue, crossprod(B, Q%*%(y-a)) + Q0%*%mu0))
test_mcmc(model = code, name = 'two-level multivariate normal', data = data, seed = 0, numItsC = 10000,
results = list(mean = list(mu = muMeanTrue),
cov = list(mu = solve(muQtrue))),
resultsTolerance = list(mean = list(mu = rep(.02,3)),
cov = list(mu = matrix(.01, 3, 3))), avoidNestedTest = TRUE)
### scalar RW updates in place of conjugate mv update
test_mcmc(model = code, name = 'two-level multivariate normal with scalar updaters', data = data, seed = 0, numItsC = 100000,
results = list(mean = list(mu = muMeanTrue),
cov = list(mu = solve(muQtrue))),
resultsTolerance = list(mean = list(mu = rep(.03,3)),
cov = list(mu = matrix(.03, 3, 3))),
samplers = list(list(type = 'RW', target = 'mu[1]'),
list(type = 'RW', target = 'mu[2]'),
list(type = 'RW', target = 'mu[3]')),
removeAllDefaultSamplers = TRUE, avoidNestedTest = TRUE)
})
test_that('another MVN conjugate sampler setup', {
set.seed(0)
prior_mean <- rep(0,5)
tmp <- array(rnorm(25), c(5,5))
tmp <- tmp + t(tmp) + 5*diag(5)
prior_cov <- tmp
a <- array(rnorm(20), c(4,5))
B <- array(NA, c(4,5,5))
for(i in c(2,4)) B[i,,] <- array(rnorm(25), c(5,5))
B[1,,] <- diag(5)
B[3,,] <- diag(5)
M_y <- array(NA, c(4,5,5))
for(i in 1:4) {
tmp <- array(rnorm(25,i), c(5,5))
tmp <- tmp + t(tmp) + 5*i*diag(5)
M_y[i,,] <- tmp
}
x <- rep(0, 5)
y <- array(rnorm(20), c(4,5))
code <- nimbleCode({
x[1:5] ~ dmnorm(mean = prior_mean[1:5], cov = prior_cov[1:5,1:5])
for(i in 1:4)
mu_y[i,1:5] <- asCol(a[i,1:5]) + B[i,1:5,1:5] %*% asCol(x[1:5])
y[1,1:5] ~ dmnorm(mu_y[1,1:5], prec = M_y[1,1:5,1:5])
y[2,1:5] ~ dmnorm(mu_y[2,1:5], cov = M_y[2,1:5,1:5])
y[3,1:5] ~ dmnorm(mu_y[3,1:5], prec = M_y[3,1:5,1:5])
y[4,1:5] ~ dmnorm(mu_y[4,1:5], cov = M_y[4,1:5,1:5])
})
constants <- list(prior_mean=prior_mean, prior_cov=prior_cov, a=a, B=B, M_y=M_y)
data <- list(y=y)
inits <- list(x=x)
Rmodel <- nimbleModel(code, constants, data, inits)
spec <- configureMCMC(Rmodel)
Rmcmc <- buildMCMC(spec)
Cmodel <- compileNimble(Rmodel)
Cmcmc <- compileNimble(Rmcmc, project = Rmodel)
set.seed(0)
Rmcmc$run(10)
Rsamples <- as.matrix(Rmcmc$mvSamples)
set.seed(0)
Cmcmc$run(10)
Csamples <- as.matrix(Cmcmc$mvSamples)
expect_equal(round(as.numeric(Rsamples), 8),
c(0.97473128, 0.50438666, 1.1251132, 0.83830666, 0.74077066, 0.92935482, 0.83758372, 0.98708273, 1.24199937, 0.67348127, -0.54387714, -0.60713969, -0.51392796, -0.3176801, -0.34416529, -0.08530564, -0.47160157, -0.21996584, -0.20504917, -0.77287122, 0.78462584, 0.46103509, 0.43862813, 0.49343096, 0.61020864, 0.55088287, 0.53887202, 0.49863894, 0.62691318, 0.80142839, 0.34941152, 0.06623608, 0.05624477, 0.21369178, 0.26585415, -0.1439989, -0.03133488, 0.3544062, -0.03518959, 0.27415746, 0.40977, 0.8351078, 0.25719293, 0.05663917, 0.30894028, 0.33113315, 0.47647909, 0.26143962, 0.07180759, 0.27255767),
info = 'R sample not correct compared to known result')
dif <- as.numeric(Rsamples - Csamples)
expect_true(max(abs(dif)) < 1E-15, info = 'R and C equiv')
y_prec <- array(NA, c(4,5,5))
y_prec[1,,] <- M_y[1,,]
y_prec[2,,] <- solve(M_y[2,,])
y_prec[3,,] <- M_y[3,,]
y_prec[4,,] <- solve(M_y[4,,])
contribution_mean <- array(NA, c(4,5))
for(i in 1:4) contribution_mean[i,] <- t(B[i,,]) %*% y_prec[i,,] %*% (y[i,] - a[i,])
contribution_prec <- array(NA, c(4,5,5))
for(i in 1:4) contribution_prec[i,,] <- t(B[i,,]) %*% y_prec[i,,] %*% B[i,,]
prior_prec <- solve(prior_cov)
post_prec <- prior_prec + apply(contribution_prec, c(2,3), sum)
post_cov <- solve(post_prec)
post_mean <- (post_cov %*% (prior_prec %*% prior_mean + apply(contribution_mean, 2, sum)))[,1]
Cmcmc$run(100000)
Csamples <- as.matrix(Cmcmc$mvSamples)
dif_mean <- as.numeric(apply(Csamples, 2, mean)) - post_mean
expect_true(max(abs(dif_mean)) < 0.001, info = 'posterior mean')
dif_cov <- as.numeric(cov(Csamples) - post_cov)
expect_true(max(abs(dif_cov)) < 0.001, info = 'posterior cov')
})
test_that('conjugate Wishart setup', {
set.seed(0)
trueCor <- matrix(c(1, .3, .7, .3, 1, -0.2, .7, -0.2, 1), 3)
covs <- c(3, 2, .5)
trueCov = diag(sqrt(covs)) %*% trueCor %*% diag(sqrt(covs))
Omega = solve(trueCov)
n = 20
R = diag(rep(1,3))
mu = 1:3
Y = mu + t(chol(trueCov)) %*% matrix(rnorm(3*n), ncol = n)
M = 3
data <- list(Y = t(Y), n = n, M = M, mu = mu, R = R)
code <- nimbleCode( {
for(i in 1:n) {
Y[i, 1:M] ~ dmnorm(mu[1:M], Omega[1:M,1:M]);
}
Omega[1:M,1:M] ~ dwish(R[1:M,1:M], 4);
})
newDf = 4 + n
newR = R + tcrossprod(Y- mu)
OmegaTrueMean = newDf * solve(newR)
wishRV <- array(0, c(M, M, 10000))
for(i in 1:10000) {
z <- t(chol(solve(newR))) %*% matrix(rnorm(3*newDf), ncol = newDf)
wishRV[ , , i] <- tcrossprod(z)
}
OmegaSimTrueSDs = apply(wishRV, c(1,2), sd)
test_mcmc(model = code, name = 'conjugate Wishart', data = data, seed = 0, numItsC = 1000, inits = list(Omega = OmegaTrueMean),
results = list(mean = list(Omega = OmegaTrueMean ),
sd = list(Omega = OmegaSimTrueSDs)),
resultsTolerance = list(mean = list(Omega = matrix(.05, M,M)),
sd = list(Omega = matrix(0.06, M, M))), avoidNestedTest = TRUE)
# issue with Chol in R MCMC - probably same issue as in jaw-linear
})
test_that('conjugate Wishart setup with scaling', {
set.seed(0)
trueCor <- matrix(c(1, .3, .7, .3, 1, -0.2, .7, -0.2, 1), 3)
covs <- c(3, 2, .5)
tau <- 4
trueCov = diag(sqrt(covs)) %*% trueCor %*% diag(sqrt(covs))
Omega = solve(trueCov) / tau
n = 20
R = diag(rep(1,3))
mu = 1:3
Y = mu + t(chol(trueCov)) %*% matrix(rnorm(3*n), ncol = n)
M = 3
data <- list(Y = t(Y), n = n, M = M, mu = mu, R = R)
code <- nimbleCode( {
for(i in 1:n) {
Y[i, 1:M] ~ dmnorm(mu[1:M], tmp[1:M,1:M])
}
tmp[1:M,1:M] <- tau * Omega[1:M,1:M]
Omega[1:M,1:M] ~ dwish(R[1:M,1:M], 4);
})
newDf = 4 + n
newR = R + tcrossprod(Y - mu)*tau
OmegaTrueMean = newDf * solve(newR)
wishRV <- array(0, c(M, M, 10000))
for(i in 1:10000) {
z <- t(chol(solve(newR))) %*% matrix(rnorm(3*newDf), ncol = newDf)
wishRV[ , , i] <- tcrossprod(z)
}
OmegaSimTrueSDs = apply(wishRV, c(1,2), sd)
m <- nimbleModel(code, data = data[1],constants=data[2:5],inits = list(Omega = OmegaTrueMean, tau = tau))
conf <- configureMCMC(m)
expect_equal(conf$getSamplers()[[1]]$name, "conjugate_dwish_dmnormAD_multiplicativeScalar",
info = "conjugate dmnormAD-dwish with scaling not detected")
test_mcmc(model = code, name = 'conjugate Wishart, scaled', data = data, seed = 0, numItsC = 1000, inits = list(Omega = OmegaTrueMean, tau = tau),
results = list(mean = list(Omega = OmegaTrueMean ),
sd = list(Omega = OmegaSimTrueSDs)),
resultsTolerance = list(mean = list(Omega = matrix(.05, M,M)),
sd = list(Omega = matrix(0.06, M, M))), avoidNestedTest = TRUE)
# issue with Chol in R MCMC - probably same issue as in jaw-linear
})
test_that('using RW_wishart sampler on non-conjugate Wishart node', {
set.seed(0)
trueCor <- matrix(c(1, .3, .7, .3, 1, -0.2, .7, -0.2, 1), 3)
covs <- c(3, 2, .5)
trueCov = diag(sqrt(covs)) %*% trueCor %*% diag(sqrt(covs))
Omega = solve(trueCov)
n = 20
R = diag(rep(1,3))
mu = 1:3
Y = mu + t(chol(trueCov)) %*% matrix(rnorm(3*n), ncol = n)
M = 3
data <- list(Y = t(Y), n = n, M = M, mu = mu, R = R)
code <- nimbleCode( {
for(i in 1:n) {
Y[i, 1:M] ~ dmnorm(mu[1:M], Omega[1:M,1:M])
}
Omega[1:M,1:M] ~ dwish(R[1:M,1:M], 4)
})
newDf = 4 + n
newR = R + tcrossprod(Y- mu)
OmegaTrueMean = newDf * solve(newR)
wishRV <- array(0, c(M, M, 10000))
for(i in 1:10000) {
z <- t(chol(solve(newR))) %*% matrix(rnorm(3*newDf), ncol = newDf)
wishRV[ , , i] <- tcrossprod(z)
}
OmegaSimTrueSDs = apply(wishRV, c(1,2), sd)
allData <- data
constants <- list(n = allData$n, M = allData$M, mu = allData$mu, R = allData$R)
data <- list(Y = allData$Y)
inits <- list(Omega = OmegaTrueMean)
Rmodel <- nimbleModel(code, constants, data, inits)
Rmodel$calculate()
conf <- configureMCMC(Rmodel, nodes = NULL)
conf$addSampler('Omega', 'RW_wishart')
Rmcmc <- buildMCMC(conf)
compiledList <- compileNimble(list(model=Rmodel, mcmc=Rmcmc))
Cmodel <- compiledList$model; Cmcmc <- compiledList$mcmc
set.seed(0)
samples <- runMCMC(Cmcmc, 10000)
d1 <- as.numeric(apply(samples, 2, mean)) - as.numeric(OmegaTrueMean)
difference <- sum(round(d1,9) - c(0.024469145, -0.011872571, -0.045035297, -0.011872571, -0.003443918, 0.009363410, -0.045035297, 0.009363410, 0.049971420))
expect_true(difference == 0)
})
test_that('using RW_wishart sampler on inverse-Wishart distribution', {
code <- nimbleCode( {
for(i in 1:n) {
Y[i, 1:M] ~ dmnorm(mu[1:M], cov = C[1:M,1:M])
}
C[1:M,1:M] ~ dinvwish(R[1:M,1:M], 4)
})
set.seed(0)
trueCor <- matrix(c(1, .3, .7, .3, 1, -0.2, .7, -0.2, 1), 3)
covs <- c(3, 2, .5)
trueCov = diag(sqrt(covs)) %*% trueCor %*% diag(sqrt(covs))
n = 20
R = diag(rep(1,3))
mu = 1:3
Y = mu + t(chol(trueCov)) %*% matrix(rnorm(3*n), ncol = n)
M = 3
data <- list(Y = t(Y), n = n, M = M, mu = mu, R = R)
newDf = 4 + n
newR = R + tcrossprod(Y- mu)
CTrueMean <- newR / newDf
CTrueMeanVec <- as.numeric(CTrueMean)
allData <- data
constants <- list(n = allData$n, M = allData$M, mu = allData$mu, R = allData$R)
data <- list(Y = allData$Y)
inits <- list(C = CTrueMean)
niter <- 50000
Rmodel <- nimbleModel(code, constants, data, inits)
Rmodel$calculate()
conf <- configureMCMC(Rmodel)
Rmcmc <- buildMCMC(conf)
compiledList <- compileNimble(list(model=Rmodel, mcmc=Rmcmc))
Cmodel <- compiledList$model; Cmcmc <- compiledList$mcmc
set.seed(0)
samples <- runMCMC(Cmcmc, niter)
conjMean <- as.numeric(apply(samples, 2, mean))
conjSD <- as.numeric(apply(samples, 2, sd))
Rmodel <- nimbleModel(code, constants, data, inits)
Rmodel$calculate()
conf <- configureMCMC(Rmodel, nodes = NULL)
conf$addSampler('C', 'RW_wishart')
Rmcmc <- buildMCMC(conf)
compiledList <- compileNimble(list(model=Rmodel, mcmc=Rmcmc))
Cmodel <- compiledList$model; Cmcmc <- compiledList$mcmc
set.seed(0)
samples <- runMCMC(Cmcmc, niter)
RWMean <- as.numeric(apply(samples, 2, mean))
RWSD <- as.numeric(apply(samples, 2, sd))
expect_true(all(round(as.numeric(RWMean - conjMean), 9) == c(-0.001651758, -0.009675571, 0.004894809, -0.009675571, 0.015533882, -0.008256095, 0.004894809, -0.008256095, 0.002119615)))
expect_true(all(round(as.numeric(RWSD - conjSD), 9) == c(0.022803503, -0.010107015, 0.012342044, -0.010107015, 0.006191412, -0.000091101, 0.012342044, -0.000091101, 0.001340032)))
})
test_that('detect conjugacy when scaling Wishart, inverse Wishart cases', {
code <- nimbleCode({
mycov[1:p, 1:p] <- lambda * Sigma[1:p,1:p] / eta
y[1:p] ~ dmnorm(z[1:p], cov = mycov[1:p, 1:p])
Sigma[1:p,1:p] ~ dinvwish(S[1:p,1:p], nu)
})
m <- nimbleModel(code, constants = list(p = 3))
expect_identical(length(m$checkConjugacy('Sigma')), 1L, 'inverse-Wishart case')
code <- nimbleCode({
mycov[1:p, 1:p] <- lambda * Sigma[1:p,1:p] / eta
y[1:p] ~ dmnorm(z[1:p], prec = mycov[1:p, 1:p])
Sigma[1:p,1:p] ~ dwish(S[1:p,1:p], nu)
})
m <- nimbleModel(code, constants = list(p = 3))
expect_identical(length(m$checkConjugacy('Sigma')), 1L, 'Wishart case')
code <- nimbleCode({
mycov[1:p, 1:p] <- lambda * Sigma[1:p,1:p] / eta
y[1:p] ~ dmnorm(z[1:p], cov = mycov[1:p, 1:p])
Sigma[1:p,1:p] ~ dwish(S[1:p,1:p], nu)
})
m <- nimbleModel(code, constants = list(p = 3))
expect_identical(length(m$checkConjugacy('Sigma')), 0L, 'inverse-Wishart not-conj case')
code <- nimbleCode({
mycov[1:p, 1:p] <- lambda * Sigma[1:p,1:p] / eta
y[1:p] ~ dmnorm(z[1:p], prec = mycov[1:p, 1:p])
Sigma[1:p,1:p] ~ dinvwish(S[1:p,1:p], nu)
})
m <- nimbleModel(code, constants = list(p = 3))
expect_identical(length(m$checkConjugacy('Sigma')), 0L, 'Wishart not-conj case')
code <- nimbleCode({
mycov[1:p, 1:p] <- lambda[1:p,1:p] * Sigma[1:p,1:p]
y[1:p] ~ dmnorm(z[1:p], cov = mycov[1:p, 1:p])
Sigma[1:p,1:p] ~ dinvwish(S[1:p,1:p], nu)
})
m <- nimbleModel(code, constants = list(p = 3))
expect_identical(length(m$checkConjugacy('Sigma')), 0L, 'Wishart case')
code <- nimbleCode({
mycov[1:p, 1:p] <- lambda[1:p,1:p] %*% Sigma[1:p,1:p]
y[1:p] ~ dmnorm(z[1:p], cov = mycov[1:p, 1:p])
Sigma[1:p,1:p] ~ dinvwish(S[1:p,1:p], nu)
})
m <- nimbleModel(code, constants = list(p = 3))
expect_identical(length(m$checkConjugacy('Sigma')), 0L, 'Wishart case')
})
test_that("realized conjugacy links are working", {
## dmnorm cases
code <- nimbleCode({
mu[1:3] ~ dmnorm(z[1:3], pr[1:3,1:3])
for(i in 1:2)
y1[i, 1:3] ~ dmnorm(mu[1:3], pr[1:3,1:3])
mn2[1:3] <- b0[1:3] + mu[1:3]
for(i in 1:2) {
y2[i, 1:3] ~ dmnorm(mn2[1:3], pr[1:3,1:3])
}
mn3[1:3] <- A[1:3,1:3]%*%mu[1:3]
for(i in 1:2) {
y3[i, 1:3] ~ dmnorm(mn3[1:3], pr[1:3,1:3])
}
mn4[1:3] <- b0[1:3] + A[1:3,1:3]%*%mu[1:3]
for(i in 1:2) {
y4[i, 1:3] ~ dmnorm(mn4[1:3], pr[1:3,1:3])
}
})
m <- nimbleModel(code, data = list (y1 = matrix(rnorm(6),2),
y2 = matrix(rnorm(6),2),
y3 = matrix(rnorm(6),2),
y4 = matrix(rnorm(6),2)),
inits = list(b0 = rnorm(3), A=matrix(1:9, 3), pr = diag(3)))
conf <- configureMCMC(m)
mcmc <- buildMCMC(conf)
expect_identical(conf$getSamplers()[[1]]$name, "conjugate_dmnormAD_dmnormAD_additive_dmnormAD_identity_dmnormAD_linear_dmnormAD_multiplicative")
expect_identical(mcmc$samplerFunctions[[1]]$N_dep_dmnormAD_identity, 2L)
expect_identical(mcmc$samplerFunctions[[1]]$N_dep_dmnormAD_additive, 2L)
expect_identical(mcmc$samplerFunctions[[1]]$N_dep_dmnormAD_multiplicative, 2L)
expect_identical(mcmc$samplerFunctions[[1]]$N_dep_dmnormAD_linear, 2L)
expect_identical(c('dep_dmnormAD_identity_coeff', 'dep_dmnormAD_additive_coeff') %in%
ls(mcmc$samplerFunctions[[1]]), rep(FALSE, 2))
expect_identical(c('dep_dmnormAD_multiplicative_coeff', 'dep_dmnormAD_linear_coeff') %in%
ls(mcmc$samplerFunctions[[1]]), rep(TRUE, 2))
expect_identical(c('dep_dmnormAD_identity_offset', 'dep_dmnormAD_multiplicative_offset') %in%
ls(mcmc$samplerFunctions[[1]]), rep(FALSE, 2))
expect_identical(c('dep_dmnormAD_additive_offset', 'dep_dmnormAD_linear_offset') %in%
ls(mcmc$samplerFunctions[[1]]), rep(TRUE, 2))
expect_identical(mcmc$samplerFunctions[[1]]$dep_dmnormAD_identity_nodeNames, c('y1[1, 1:3]', 'y1[2, 1:3]'))
expect_identical(mcmc$samplerFunctions[[1]]$dep_dmnormAD_additive_nodeNames, c('y2[1, 1:3]', 'y2[2, 1:3]'))
expect_identical(mcmc$samplerFunctions[[1]]$dep_dmnormAD_multiplicative_nodeNames, c('y3[1, 1:3]', 'y3[2, 1:3]'))
expect_identical(mcmc$samplerFunctions[[1]]$dep_dmnormAD_linear_nodeNames, c('y4[1, 1:3]', 'y4[2, 1:3]'))
## dwish case
code <- nimbleCode({
for(i in 1:2) {
y1[i, 1:3] ~ dmnorm(mu[1:3], pr[1:3,1:3])
}
pr2[1:3,1:3] <- d*pr[1:3,1:3]
for(i in 1:2) {
y2[i, 1:3] ~ dmnorm(mu[1:3], pr2[1:3,1:3])
}
pr[1:3,1:3] ~ dwish(R[1:3,1:3], 8)
})
m <- nimbleModel(code, data = list (y1 = matrix(rnorm(6),2),
y2 = matrix(rnorm(6),2)),
inits = list(pr = diag(3), R = diag(3)))
conf <- configureMCMC(m)
mcmc <- buildMCMC(conf)
expect_identical(conf$getSamplers()[[1]]$name, "conjugate_dwish_dmnormAD_identity_dmnormAD_multiplicativeScalar")
expect_identical(mcmc$samplerFunctions[[1]]$N_dep_dmnormAD_identity, 2L)
expect_identical(mcmc$samplerFunctions[[1]]$N_dep_dmnormAD_multiplicativeScalar, 2L)
expect_identical('dep_dmnormAD_identity_coeff' %in%
ls(mcmc$samplerFunctions[[1]]), FALSE)
expect_identical('dep_dmnormAD_multiplicativeScalar_coeff' %in%
ls(mcmc$samplerFunctions[[1]]), TRUE)
expect_identical(c('dep_dmnormAD_identity_offset', 'dep_dmnormAD_multiplicativeScalar_offset') %in%
ls(mcmc$samplerFunctions[[1]]), rep(FALSE, 2))
expect_identical(mcmc$samplerFunctions[[1]]$dep_dmnormAD_identity_nodeNames, c('y1[1, 1:3]', 'y1[2, 1:3]'))
expect_identical(mcmc$samplerFunctions[[1]]$dep_dmnormAD_multiplicativeScalar_nodeNames, c('y2[1, 1:3]', 'y2[2, 1:3]'))
})
options(warn = RwarnLevel)
nimbleOptions(verbose = nimbleVerboseSetting)
nimbleOptions(MCMCprogressBar = nimbleProgressBarSetting)
nimbleOptions(buildModelDerivs = BMDopt)
Any scripts or data that you put into this service are public.
Add the following code to your website.
For more information on customizing the embed code, read Embedding Snippets.