-
Notifications
You must be signed in to change notification settings - Fork 23
Multivariate normal conjugacy
Currently dmnorm conjugacy always numerically calculates a 'coeff' matrix and 'offset' vector so as to handle conjugacy in situations with dependencies like y~dmnorm(A*mu+b, Q) for target 'mu'. Here A is coeff and b is offset.
I'd like to avoid run-time recalculation of coeff and offset when we can detect the following cases:
y~dmnorm(mu,Q)
y~dmnorm(mu+b),Q
y~dmnorm(A*mu,Q)
y~dmnorm(A*mu+b,Q)
Per discussion at 4/5/17 meeting, we could generate individualized getCoeff and getOffset (or getContributionPrec and getContributionMean) nimbleFunctions. More simply, we might use functionality in current linearity checker to pull out coeff and offset variables (including index blocks) and hard-code those into the conjugate sampler.
Old notes from Chris:
I see two paths forward here:
- At the stage of processing BUGS code, convert dmnorm when appropriate to dmnorm_simple, dmnorm_offset, dmnorm_coeff, and dmnorm_linear that have coeff and offset parameters as appropriate.
Then in conjugacy checking add to the control argument information about which dependent nodes we know the coeff and offset. Then pass the enhanced control object in when we generate the dmnorm conjugate sampler so that for relevant dependencies, we use getParam(node, 'coeff') and getParam(node, 'offset') as appropriate rather than numerically calculating them.
- Alternatively, don't add new dmnorm variants. Rather when we create the control argument include coeff and offset expressions for relevant dependent nodes. E.g., for
y~dmnorm(A[1:3,1:3]*mu[1:3]+b[1:3],Q), coeff would be 'A[1:3,1:3]'. Then when we generate the sampler nimbleFunction, do things likedep_dmnorm_coeff[i,,] = model[[coeff[i]]]
In conjugacy checking, we'll need to do some parsing of the 'mean' for each dependent to be able to pick out the correct variables with their indices, and correctly handle if the expression is more complicated than A*mu+b.
Note that if we simply have y~dmnorm(mu,Q) we'll want to avoid any calculations from the "missing" coeff and offset.