Changelog¶
0.4.0-alpha (2026-10-05)¶
Breaking changes¶
simple_param_specsandSimpleMatrixnow take their default as a 1D tensor of shape(1,). A default passed as a float raises aTypeError, and a tensor of another shape aValueError.Parameter names must be non-empty and must not contain
"/", which the path syntax ofset_param_specsreserves as its separator. Operand names in an operator follow the same rule.
New features¶
New operators:
Product, the matrix product \(V = A B\) of exactly two operands;Transpose, \(V = A^\top\);Stack, binding two or more operands row-wise; andInverse, \(V = A^{-1}\), whose gradient reuses the inverse computed in the forward pass. As with the other operators, each operand may be a trainable matrix or a fixed tensor.Matrix.set_param_specs, updating one or more parameter specifications in place. A key without a trailing"/"addresses one parameter exactly, while a key ending with"/"addresses a subtree:"A/"every parameter of the operand"A", nested operands below it included, and"/"every parameter of the matrix. Each field passed replaces that field of every resolved specification and fields left asNoneare kept, so a call without fields changes nothing. Values are assigned as given, without validation or copying, and take effect on the next call.Matrix.cacheand the cache controlsenable_cache,disable_cacheandreset_intermediates. Disabling the cache also clears it, so an entry stored while caching was on cannot come back when it is turned on again.Operatoroverrides all three to recurse into its matrix operands andAdapterinto its adaptee, so one call covers a whole composite.
Changes¶
MarginalREML.ai_stepnow resolves the dtype and device fromthetaalone and convertsxandyto them, rather than resolving a common dtype and device from the three.
Documentation¶
Added API reference pages for
Product,Transpose,StackandInverse, listed them on the operators page, and regenerated the per-class pages.
Testing¶
Added test modules and planning documents for
Product,Transpose,StackandInverse.
0.3.0-alpha (2026-09-20)¶
Breaking changes¶
IdentityMatrixandDummyMatrixno longer acceptdtypeanddevicearguments. Both follow the dtype and the device of their input instead, falling back to the PyTorch defaults when they receive none.MarginalREML.get_thetaandMarginalREML.get_betano longer accept ahistoryargument, always reading the history populated byoptimize.A composite covariance matrix is now built on a single dtype and device. Where the operands’ own defaults disagree and no input parameters override them, a
ValueErroris raised instead oftorch.catsilently promoting.
New features¶
Operator.call_tree, a debugging view of a composite. It returns two dictionaries over one key set, keyed by the path to each node — the operand names leading to it joined with"/", rooted at"/"— holding the matrix every node evaluated to and the free parameter slice that node received. Nested operators are reached by recursing throughcall_treerather than by capturing the calls a forward pass makes, so the tree is complete whether or not an intermediate cache is warm.Operator.grad_tree, the gradient counterpart over the same keys: each node’s(grad, grad_names)pair, in that node’s own shape, alongside the same parameter slices. A node’s names are namespaced from that node, so joining the path to a name gives the name the composite exposes infree_param_names.Matrix.get_default_dtype_device, reporting the dtype and device that would be resolved from the current parameters.
Changes¶
The dtype and device of a composite are resolved once for the whole structure: the input parameters first, then the free-parameter defaults of the
Matrixoperands, then Torch’s defaults. Input parameters override every default. Fixed tensor operands are never a resolution source — they are cast to follow. The operators and the identity and dummy matrices now observe the resolved dtype and device rather than fixing their own, and the identity and dummy matrices return a clone so a cached result cannot be mutated by the caller.The intermediate cache compares parameter values elementwise rather than hashing them, removing the dependency on
torch.hash_tensorand the limitation it imposed on MPS. A copy of the parameter tensor is stored, so a later in-place edit of the caller’s tensor cannot change the key of an entry already cached.Adapterno longer forces itsparam_specs;param_mapnow receives the free, untransformed parameters.
Bug fixes¶
Fixed silent dtype promotion in the operators, where
torch.catwould promote the results of the operands.Fixed the parameter conversions between dicts and tensors, including the empty case, which now yields an empty tensor rather than failing.
Matrix.auto_gradreturns(None, [])for a matrix without free parameters without building a Jacobian, andtrans_gradreturns an empty tensor where appropriate.The covariance matrices now validate
free_paramsthroughbuild_paramsbefore returning early for a matrix without free parameters, so invalid input raises even there.SimpleMatrixvalidates its input before passing it on.Corrected the documented shapes in
MarginalREML, whose score and AI matrix are sized by the number of free parameters.
Documentation¶
Regenerated and extended the API reference, adding pages for
Adapter,Augment,Gramand the post-estimation functions.Documented the single dtype and device contract on
Operator, and the cost ofcall_treeandgrad_tree.
Testing¶
Added test modules for the adapter and for
Augment, and extended the operator, matrix, identity, dummy and scalar matrix suites to cover the dtype and device contract and the two new tree methods. Device tests follow the accelerator available at run time.Added a test plan document beside each test module under
tests/covariance, recording what must be covered and the risks worth testing.
0.2.0-alpha (2026-09-15)¶
Breaking changes¶
Renamed the
REMLestimator toMarginalREML. The moduletorch_openreml.remlis nowtorch_openreml.marginal_reml, andtorch_openreml.REMLis no longer available.MarginalREMLnow takes a singleMatrixinstance as its only argument. The previous functional interface (v_builder,map_theta_to_v,map_theta_to_gandmap_theta_to_dv) has been removed.Reworked the
Matrixparameter interface. The constructor now takes a singleparam_specsdictionary in place ofparam_names,transandno_grad_index. Each parameter is specified by its own dictionary with the keys"fixed","default"and"trans", so fixed and free parameters can be described together, each with an individual default and transform.Removed
Matrix.from_param_dict,Matrix.to_param_dict,Matrix.map_theta_to_v,Matrix.map_theta_to_dv,Matrix.set_no_gradandMatrix.check_params. Usebuild_paramsand theparam_specsaccessors instead.Matrix.__call__,grad,auto_grad,manual_gradandtrans_gradnow take an optionalfree_paramsargument. When it is omitted, the default value of each free parameter is used, so a matrix can be evaluated without supplying parameters explicitly.Post-estimation methods
marginal_predict,marginal_residualandblupwere removed from the estimator. All post-estimation quantities are now computed by the module-level functions intorch_openreml.post.MarginalREMLkeepsblue,predict,residualandloglikas convenience methods.Removed
utils.categorical_to_design_matrix. Categorical encoding is handled byDummyMatrix.
New features¶
New covariance matrices:
EqualEntryMatrix,UnconstrainedMatrix,LowerTriangularMatrixandSimpleMatrix.New
Adaptermatrix, which reparameterises an existing matrix through a user-supplied mapping from the adapter’s parameters to the adaptee’s parameters, allowing parameters to be combined, split or constrained.New operators:
Gram, computing \(X^\top X\) or \(X X^\top\), andAugment, binding operands column-wise.New
torch_openreml.postmodule with the post-estimation functionsblue,blup,marginal_predict,marginal_residual,predict,residualandloglik, operating directly on tensors.New
simple_param_specshelper for building parameter specifications with a common transform and default.Trace approximation in
MarginalREML.ai_stepandoptimizeaccepttrace_approxandsubspace_fraction, which estimate the trace term of the score from a random subspace instead of computing it exactly.optimizealso acceptsexact_score_threshold, below which the exact score is used again so that convergence is not affected by the approximation.Configurable differentiation.
Matrixexposes agrad_modeattribute ("manual","auto"or"default") and ajacobian_methodattribute, together withjacobian_chunk_size.The package now exposes
__version__.
Changes¶
The default Jacobian method for automatic differentiation is now
"jacfwd", which avoids the memory blow-up that"jacrev"suffers as the matrix dimension grows.identity_matrix,scalar_matrixand the operators were updated to the newparam_specsparameter interface.DummyMatrixgained adrop_empty_colsoption for dropping columns that contain no observations.TransformIdentitynow returns a result of the same length as its input.CompoundSymmetricMatrixandEquicorrelationMatrixnow raise an error forn = 1.
Bug fixes¶
Fixed incorrect gradient computation in
DiagonalMatrix, including the gradient masking and the selection of the manual gradient for all parameters.Fixed
BlockDiagonalwhenfree_paramswas passed as a dictionary.Fixed an empty-tensor concatenation bug in
Matrix.Fixed the gradient and the inverse of
TransformPow.Fixed
Operatorso that nested operators and matrices have their intermediates reset correctly during automatic differentiation.Fixed the operators so that free parameter defaults are used when
free_paramsisNone.
Documentation¶
Added this changelog, a vignette on marginal REML, and a guide for using
torch-openremlfrom R viareticulate.Restructured the API reference, adding pages for the adapter, post-estimation functions and the new matrices and operators.
Rewrote the README with the package overview, features and installation instructions.
Testing¶
Added a pytest suite under
tests/covariancecovering the matrices, the operators, the transforms,utilsand the example data, and registered it as the default test path inpyproject.toml.
0.1.0-alpha (2026-05-08)¶
First release of
torch-openreml