TuckerTensorTrain.entries_ambient_transpose#
- static t3toolbox.tucker_tensor_train.TuckerTensorTrain.entries_ambient_transpose(c, index, shape, sum_over_probes=False)#
def entries_ambient_transpose( c: NDArray, # residual, shape = W + C index: NDArray, # int, shape = (d,) + W shape: Sequence[int], # ambient dims (N0, ..., N(d-1)) sum_over_probes: bool = False, ) -> Sequence[NDArray]: # canonical (CP) factors, len=d, elm_shape = stack + (R, Ni)
Ambient transpose of
entries(): scattercatindexinto canonical (CP) factors.The
entriescounterpart ofapply_ambient_transpose()– identical, with the apply vectors replaced by the unit vectorse_{index_k}, so the CP factors are one-hots and the back-projection isc * e_{idx_0} (x) ... (x) e_{idx_{d-1}}. See that method (anddocs/transposes.md) for the ambient vs corewise vs tangent distinction – this is the ambient one (the frame-free adjoint on the full tensor space); the gradient-for-optimizers versions areentries_corewise_transposeandT3Tangent.entries_transpose.sum_over_probes=TruemakesWthe CP rank (scatter-adding colliding indices – theJ^T rfor entry sampling);FalsekeepsWas a stacking axis.shapesupplies the ambient dims(N0, ..., N(d-1)), which (unlikeapply_ambient_transpose(), wherewwcarries them)candindexalone do not determine. Returns CPfactorsforfrom_canonical().Examples
Back-projecting a residual scatters it at the index (realize the CP factors with
from_canonical()):>>> import numpy as np >>> import t3toolbox.tucker_tensor_train as t3 >>> x = t3.TuckerTensorTrain.randn((10, 11, 12), (5, 6, 4), (1, 2, 3, 1)) >>> factors = t3.TuckerTensorTrain.entries_ambient_transpose(2.0, (3, 5, 7), x.shape) >>> ETc = t3.TuckerTensorTrain.from_canonical(factors) >>> print(bool(abs(float(ETc.to_dense()[3, 5, 7]) - 2.0) < 1e-9)) # c lands at the index True >>> rest = ETc.to_dense().copy(); rest[3, 5, 7] = 0.0 >>> print(bool(np.linalg.norm(rest) < 1e-9)) # zero elsewhere True