Sparse Tensor (pyttb.sptensor)

For all examples in this document, the following module imports are assumed:

>>> import pyttb as ttb
>>> import numpy as np
class pyttb.sptensor(subs: ndarray | None = None, vals: ndarray | None = None, shape: int | Iterable[int] | None = None, copy: bool = True)[source]

Class for sparse tensors.

Parameters:
  • subs (optional) – Subscripts of the nonzero values in the sparse tensor as an numpy.ndarray. Row k specifies the subscripts of the k-th value in vals.

  • vals (optional) – Data elements of the sparse tensor.

  • shape (optional) – Shape of the sparse tensor as a tuple or any iterable array of integers. If shape is not given, defaults to the minimal shape that accommodates the maximum indices provided across each dimension in subs.

  • copy (optional) – Whether to deep copy (versus reference) subs and vals. By default, subs and vals are deep copied.


Examples

Create a pyttb.sptensor from subscripts and values:

>>> shape = (4, 4, 4)
>>> subs = np.array([[1, 2, 1], [1, 3, 1]])
>>> vals = np.array([[6], [7]])
>>> S = ttb.sptensor(subs, vals, shape)
>>> S
sparse tensor of shape (4, 4, 4) with 2 nonzeros and order F
[1, 2, 1] = 6
[1, 3, 1] = 7

Create an empty pyttb.sptensor:

>>> shape = (2, 3, 4)
>>> S = ttb.sptensor(shape=shape)
>>> S
empty sparse tensor of shape (2, 3, 4) with order F

Notes

Instances of pyttb.sptensor can also be created using the following:


Tutorial

See the Sparse Tensors tutorial for getting started with the sptensor class.


Attributes and Methods

subs

Subscripts of the nonzeros.

vals

Nonzero values.

shape: tuple[()] | tuple[int, ...]

Shape of the tensor.

property ndims: int

Number of dimensions of the pyttb.sptensor.

Examples

Create a pyttb.sptensor and return the number of dimensions:

>>> S = ttb.sptensor(shape=(1, 2, 3, 4, 5, 6))
>>> S
empty sparse tensor of shape (1, 2, 3, 4, 5, 6) with order F
>>> S.ndims
6
property nnz: int

Number of nonzero values in the pyttb.sptensor.

Examples

Create a pyttb.sptensor from a 3-way diagonal pyttb.tensor and return the number of nonzeros:

>>> S = ttb.tendiag(np.ones(3)).to_sptensor()
>>> S.nnz
3
property order: Literal['F']

Return the data layout of the underlying storage.

classmethod from_aggregator(subs: ndarray, vals: ndarray, shape: int | Iterable[int] | None = None, function_handle: str | Callable[[Any], float | ndarray] = 'sum') sptensor[source]

Construct a pyttb.sptensor from an aggregation of data.

Constructed from a set of subs (subscripts), vals (values), and shape after an aggregation function is applied to the values. Note that the default aggregator function is numpy.sum(), and the shape of the sparse tensor is inferred from the subscripts.

Parameters:
  • subs – Subscripts of nonzero entries.

  • vals – Values for nonzero entries.

  • shape – Shape of sparse tensor.

  • function_handle – Aggregation function, or name of supported aggregation function from numpy_groupies.

Examples

Create a pyttb.sptensor with some duplicate subscripts and use an aggregator function to sum the values across those duplicate subscripts:

>>> subs = np.array([[1, 2, 3], [1, 3, 4], [1, 3, 4]])
>>> vals = np.array([[6], [7], [8]])
>>> shape = (4, 4)
>>> S = ttb.sptensor.from_aggregator(subs, vals)
>>> print(S)
sparse tensor of shape (2, 4, 5) with 2 nonzeros and order F
[1, 2, 3] = 6
[1, 3, 4] = 15

Create another pyttb.sptensor but specify the shape explicitly:

>>> shape = (4, 5, 6)
>>> S = ttb.sptensor.from_aggregator(subs, vals, shape)
>>> print(S)
sparse tensor of shape (4, 5, 6) with 2 nonzeros and order F
[1, 2, 3] = 6
[1, 3, 4] = 15

Create another pyttb.sptensor but aggregate using the mean of values corresponding to duplicate subscripts:

>>> S3 = ttb.sptensor.from_aggregator(
...     subs, vals, shape, function_handle=np.mean
... )
>>> print(S3)
sparse tensor of shape (4, 5, 6) with 2 nonzeros and order F
[1, 2, 3] = 6.0
[1, 3, 4] = 7.5
classmethod from_function(function_handle: Callable[[tuple[int, ...]], ndarray], shape: int | Iterable[int], nonzeros: float) sptensor[source]

Construct a pyttb.sptensor with data from a function.

Constructed with nonzeros set using a function. The subscripts of the nonzero elements of the sparse tensor are generated randomly using numpy, so calling numpy.random.seed() before using this method will provide reproducible results.

Parameters:

Examples

Create a pyttb.sptensor with entries taken from a uniform random distribution:

>>> np.random.seed(1)
>>> S = ttb.sptensor.from_function(np.random.random_sample, (2, 3, 4), 5)
>>> print(S)  
sparse tensor of shape (2, 3, 4) with 5 nonzeros and order F
[0, 1, 3] = 0.4478...
[0, 2, 0] = 0.9085...
[1, 2, 0] = 0.2936...
[1, 2, 1] = 0.2877...
[1, 2, 2] = 0.1300...

Create a pyttb.sptensor with entries equal to 1:

>>> np.random.seed(1)
>>> S = ttb.sptensor.from_function(np.ones, (2, 3, 4), 5)
>>> print(S)
sparse tensor of shape (2, 3, 4) with 5 nonzeros and order F
[0, 1, 3] = 1.0
[0, 2, 0] = 1.0
[1, 2, 0] = 1.0
[1, 2, 1] = 1.0
[1, 2, 2] = 1.0
allsubs() ndarray[source]

Generate all possible subscripts for the pyttb.sptensor.

Examples

Create an empty pyttb.sptensor and generate all subscripts:

>>> S = ttb.sptensor(shape=(2, 2, 2))
>>> S.allsubs()
array([[0, 0, 0],
       [0, 0, 1],
       [0, 1, 0],
       [0, 1, 1],
       [1, 0, 0],
       [1, 0, 1],
       [1, 1, 0],
       [1, 1, 1]])
collapse(dims: None, function_handle: collections.abc.Callable[[numpy.ndarray], float | numpy.ndarray]) float[source]
collapse(dims: int | float | collections.abc.Iterable[int] | collections.abc.Iterable[float] | numpy.ndarray, function_handle: collections.abc.Callable[[numpy.ndarray], float | numpy.ndarray] = sum) numpy.ndarray | pyttb.sptensor.sptensor
collapse(dims: int | float | Iterable[int] | Iterable[float] | ndarray | None = None, function_handle: Callable[[ndarray], float | ndarray] = sum) float | ndarray | sptensor

Collapse the pyttb.sptensor along specified dimensions.

Returns scalar (if all dimensions collapsed), numpy.ndarray (if all but one dimension collapsed), or pyttb.sptensor.

Parameters:
  • dims (optional) – Dimensions to collapse (default: all).

  • function_handle (optional) – Function used to collapse dimensions (default: numpy.sum()).

Examples

Create a pyttb.sptensor with two elements and collapse across all dimensions, resulting in a scalar value:

>>> subs = np.array([[1, 0, 1], [0, 1, 0]])
>>> vals = np.array([[6.0], [7.0]])
>>> shape = (2, 2, 2)
>>> S = ttb.sptensor(subs, vals, shape)
>>> S.collapse()
13.0

Collapse across a single dimension, resulting in a pyttb.sptensor:

>>> S.collapse(dims=np.array([0]))
sparse tensor of shape (2, 2) with 2 nonzeros and order F
[0, 1] = 6.0
[1, 0] = 7.0

Collapse across all but one dimension, resulting in a numpy.ndarray:

>>> S.collapse(dims=np.array([0, 2]))
array([6., 7.])
contract(i_0: int, i_1: int) ndarray | sptensor | tensor[source]

Contract the pyttb.sptensor along two dimensions.

If the result is sufficiently dense, it is returned as a pyttb.tensor.

Parameters:
  • i_0 – First dimension.

  • i_1 – Second dimension.

Examples

Create a pyttb.sptensor from a pyttb.tensor and contract, resulting in a dense tensor, since the result is dense:

>>> T = ttb.tensor(np.ones((2, 2, 2)))
>>> S = T.to_sptensor()
>>> S.contract(0, 1)
tensor of shape (2,) with order F
data[:] =
[2. 2.]

Create a pyttb.sptensor and contract, resulting in a pyttb.sptensor since the result is sparse:

>>> subs = np.array([[1, 1, 1], [2, 2, 2]])
>>> vals = np.array([[0.5], [1.5]])
>>> shape = (4, 4, 4)
>>> S = ttb.sptensor(subs, vals, shape)
>>> S.contract(1, 2)
sparse tensor of shape (4,) with 2 nonzeros and order F
[1] = 0.5
[2] = 1.5
copy() sptensor[source]

Return a deep copy of the pyttb.sptensor.

Examples

Create a pyttb.sptensor, make a deep copy, and verify the deep copy is not just a reference to the original:

>>> S1 = ttb.sptensor(shape=(2, 2, 2))
>>> S1[0, 0, 0] = 1
>>> # create reference to S1
>>> S2 = S1
>>> # create copy of S1
>>> S3 = S1.copy()
>>> S1[0, 0, 0] = 3
>>> S1[0, 0, 0] == S2[0, 0, 0]
True
>>> S1[0, 0, 0] == S3[0, 0, 0]
False
double(immutable: bool = False) ndarray[source]

Convert pyttb.sptensor to a numpy.ndarray of doubles.

Parameters:

immutable – Whether or not the returned data can be mutated. May enable additional optimizations.

Examples

Create a pyttb.sptensor with two elements and convert it to a numpy.ndarray:

>>> S = ttb.sptensor()
>>> S[0, 1, 2] = 1.5
>>> S
sparse tensor of shape (1, 2, 3) with 1 nonzeros and order F
[0, 1, 2] = 1.5
>>> S.double()
array([[[0. , 0. , 0. ],
        [0. , 0. , 1.5]]])
elemfun(function_handle: Callable[[ndarray], ndarray]) sptensor[source]

Apply a function to the nonzero elements of the pyttb.sptensor.

Returns a copy of the sparse tensor with the updated values.

Parameters:

function_handle – Function to apply to all values.

Examples

Create a pyttb.sptensor and multiply each nonzero element by 2:

>>> S1 = ttb.sptensor()
>>> S1[2, 2, 2] = 1.5
>>> S2 = S1.elemfun(lambda values: values * 2)
>>> S2
sparse tensor of shape (3, 3, 3) with 1 nonzeros and order F
[2, 2, 2] = 3.0
extract(searchsubs: ndarray) ndarray[source]

Extract value from the pyttb.sptensor.

Parameters:

searchsubs – subscripts to find.

See also

__getitem__()

find() tuple[ndarray, ndarray][source]

Find subscripts of nonzero elements in the pyttb.sptensor.

Examples

Create a pyttb.sptensor with two nonzero elements and find the subscripts and associated values:

>>> S = ttb.sptensor()
>>> S[0, 1, 2] = 1
>>> S[2, 1, 0] = 2
>>> vals, subs = S.find()
>>> vals
array([[0, 1, 2],
       [2, 1, 0]])
>>> subs
array([[1.],
       [2.]])
full() tensor[source]

Convert the pyttb.sptensor to a pyttb.tensor.

Examples

Create a pyttb.sptensor and convert it to a pyttb.tensor:

>>> S = ttb.sptensor()
>>> S[1, 1, 1] = 1
>>> S.to_tensor()
tensor of shape (2, 2, 2) with order F
data[:, :, 0] =
[[0. 0.]
 [0. 0.]]
data[:, :, 1] =
[[0. 0.]
 [0. 1.]]
innerprod(other: sptensor | tensor | ktensor | ttensor) float[source]

Efficient inner product between a sparse tensor and other tensor.

Parameters:

other – Tensor to take an inner product with.

Examples

Create a pyttb.sptensor:

>>> S = ttb.sptensor()
>>> S[0, 0, 0] = 1
>>> S[1, 1, 1] = 2
>>> S
sparse tensor of shape (2, 2, 2) with 2 nonzeros and order F
[0, 0, 0] = 1.0
[1, 1, 1] = 2.0

Compute inner product with pyttb.tensor of all ones that is the same shape as S:

>>> T = ttb.tenones(S.shape)
>>> S.innerprod(T)
3.0

Compute inner product with rank-1 pyttb.ktensor of all ones that is the same shape as S:

>>> factor_matrices = [np.ones((s, 1)) for s in S.shape]
>>> K = ttb.ktensor(factor_matrices)
>>> S.innerprod(K)
3.0
isequal(other: sptensor | tensor) bool[source]

Exact equality for sparse tensors.

Parameters:

other – Tensor to compare against.

Examples

Create a pyttb.sptensor:

>>> S = ttb.sptensor()
>>> S[0, 0, 0] = 1
>>> S[1, 1, 1] = 2
>>> S
sparse tensor of shape (2, 2, 2) with 2 nonzeros and order F
[0, 0, 0] = 1.0
[1, 1, 1] = 2.0

Compare with a tensor that should be equal:

>>> T = S.to_tensor()
>>> S.isequal(T)
True

Compare with a tensor that should not be equal:

>>> T[0, 0, 0] = T[0, 0, 0] + 1
>>> S.isequal(T)
False
logical_and(other: float | sptensor | tensor) sptensor[source]

Logical AND for sparse tensors.

Parameters:

other – Other object to perform and with.

Examples

Create a pyttb.sptensor:

>>> S = ttb.sptensor(shape=(2, 2, 2))
>>> S[0, 0, 0] = 1
>>> S[1, 1, 1] = 2
>>> S
sparse tensor of shape (2, 2, 2) with 2 nonzeros and order F
[0, 0, 0] = 1.0
[1, 1, 1] = 2.0

Compute logical AND with a pyttb.tensor that has the same nonzero pattern but different values:

>>> T = S.to_tensor()
>>> T[0, 0, 0] = T[0, 0, 0] + 1
>>> S.logical_and(T)
sparse tensor of shape (2, 2, 2) with 2 nonzeros and order F
[0, 0, 0] = 1.0
[1, 1, 1] = 1.0

Compute logical AND with a scalar value:

>>> S.logical_and(1.0)
sparse tensor of shape (2, 2, 2) with 2 nonzeros and order F
[0, 0, 0] = 1.0
[1, 1, 1] = 1.0
logical_not() sptensor[source]

Logical NOT for sparse tensors.

Examples

Create a pyttb.sptensor and compute logical NOT:

>>> S = ttb.sptensor()
>>> S[0, 0, 0] = 1
>>> S[1, 1, 1] = 2
>>> S
sparse tensor of shape (2, 2, 2) with 2 nonzeros and order F
[0, 0, 0] = 1.0
[1, 1, 1] = 2.0
>>> S.logical_not()
sparse tensor of shape (2, 2, 2) with 6 nonzeros and order F
[0, 0, 1] = 1.0
[0, 1, 0] = 1.0
[0, 1, 1] = 1.0
[1, 0, 0] = 1.0
[1, 0, 1] = 1.0
[1, 1, 0] = 1.0
logical_or(other: float | pyttb.tensor.tensor) pyttb.tensor.tensor[source]
logical_or(other: pyttb.sptensor.sptensor) pyttb.sptensor.sptensor
logical_or(other: float | tensor | sptensor) tensor | sptensor

Logical OR for sparse tensors.

Parameters:

other – Object to compute OR against.

Examples

Create a pyttb.sptensor and compute logical OR with itself:

>>> S = ttb.sptensor()
>>> S[0, 0, 0] = 1
>>> S[1, 1, 1] = 2
>>> S.logical_or(S)
sparse tensor of shape (2, 2, 2) with 2 nonzeros and order F
[0, 0, 0] = 1.0
[1, 1, 1] = 1.0

Compute logical OR with a pyttb.tensor that has the same nonzero pattern:

>>> T = S.to_tensor()
>>> S.logical_or(T)
tensor of shape (2, 2, 2) with order F
data[:, :, 0] =
[[1. 0.]
 [0. 0.]]
data[:, :, 1] =
[[0. 0.]
 [0. 1.]]

Compute logical OR with a scalar value:

>>> S.logical_or(1)
tensor of shape (2, 2, 2) with order F
data[:, :, 0] =
[[1. 1.]
 [1. 1.]]
data[:, :, 1] =
[[1. 1.]
 [1. 1.]]
logical_xor(other: float | pyttb.tensor.tensor) pyttb.tensor.tensor[source]
logical_xor(other: pyttb.sptensor.sptensor) pyttb.sptensor.sptensor
logical_xor(other: float | tensor | sptensor) tensor | sptensor

Logical XOR for sparse tensors.

Parameters:

other – Object to compute XOR against.

Examples

Create a pyttb.sptensor and compute logical XOR with itself:

>>> S = ttb.sptensor()
>>> S[0, 0, 0] = 1
>>> S[1, 1, 1] = 2
>>> S.logical_xor(S)
empty sparse tensor of shape (2, 2, 2) with order F

Compute logical XOR with pyttb.tensor that has a different nonzero pattern:

>>> T = S.to_tensor()
>>> T[1, 0, 1] = 1.0
>>> S.logical_xor(T)
tensor of shape (2, 2, 2) with order F
data[:, :, 0] =
[[0. 0.]
 [0. 0.]]
data[:, :, 1] =
[[0. 0.]
 [1. 0.]]

Compute logical XOR with a scalar value:

>>> S.logical_xor(1)
tensor of shape (2, 2, 2) with order F
data[:, :, 0] =
[[0. 1.]
 [1. 1.]]
data[:, :, 1] =
[[1. 1.]
 [1. 0.]]
mask(W: sptensor) ndarray[source]

Extract non-zero values at locations specified by sparse mask tensor W.

The values in the sparse tensor corresponding to nonzeros in W will be returned as a column vector.

Parameters:

W – Mask tensor.

Examples

Create a pyttb.sptensor:

>>> S = ttb.sptensor()
>>> S[0, 0, 0] = 1
>>> S[1, 1, 1] = 2
>>> S
sparse tensor of shape (2, 2, 2) with 2 nonzeros and order F
[0, 0, 0] = 1.0
[1, 1, 1] = 2.0

Create mask pyttb.sptensor and extract nonzero values from S:

>>> W = ttb.sptensor()
>>> W[0, 0, 0] = 1
>>> W[1, 1, 1] = 1
>>> S.mask(W)
array([[1.],
       [2.]])

Create mask pyttb.sptensor and extract some nonzero values and some zero values:

>>> W = ttb.sptensor()
>>> W[0, 0, 0] = 1
>>> W[1, 0, 0] = 1
>>> S.mask(W)
array([[1.],
       [0.]])
mttkrp(U: ktensor | Sequence[ndarray], n: int | integer) ndarray[source]

Matricized tensor times Khatri-Rao product using pyttb.sptensor.

This is an efficient form of the matrix product that avoids explicitly computing the matricized sparse tensor and the large intermediate Khatri-Rao product arrays.

If the input includes a list of 2-D arrays (factor_matrices), this computes a matrix product of the mode-n matricization of the sparse tensor with the Khatri-Rao product of all arrays in the list except the n th. The length of the list of arrays must equal the number of dimensions of the sparse tensor. The shapes of each array must have leading dimensions equal to the dimensions of the sparse tensor and the same second dimension.

If the input is a pyttb.ktensor, this computes a matrix product of the mode-n matricization of the sparse tensor with the Khatri-Rao product formed by the factor_matrices and weights from the ktensor, excluding the n th factor matrix and corresponding weight. The shape of the ktensor must be compatible with the shape of the sparse tensor.

Parameters:
  • U – Factor matrix or list of factor matrices.

  • n – Mode used to matricize the pyttb.sptensor.

Examples

Create list of factor matrices:

>>> A = np.ones((4, 4))
>>> U = [A, A, A]

Create a pyttb.sptensor and compute the matricized tensor times Khatri-Rao product between it and the factor matrices:

>>> subs = np.array([[1, 1, 1], [1, 1, 3], [2, 2, 2], [3, 3, 3]])
>>> vals = np.array([[0.5], [1.5], [2.5], [3.5]])
>>> shape = (4, 4, 4)
>>> S = ttb.sptensor(subs, vals, shape)
>>> S.mttkrp(U, 0)
array([[0. , 0. , 0. , 0. ],
       [2. , 2. , 2. , 2. ],
       [2.5, 2.5, 2.5, 2.5],
       [3.5, 3.5, 3.5, 3.5]])
norm() float[source]

Compute the norm of the pyttb.sptensor.

Frobenius norm, or square root of the sum of squares of entries.

Examples

Create a pyttb.sptensor from a diagonal tensor and compute its norm:

>>> S = ttb.tendiag(np.array([1.0, 2.0, 3.0, 4.0])).to_sptensor()
>>> S
sparse tensor of shape (4, 4, 4, 4) with 4 nonzeros and order F
[0, 0, 0, 0] = 1.0
[1, 1, 1, 1] = 2.0
[2, 2, 2, 2] = 3.0
[3, 3, 3, 3] = 4.0
>>> S.norm()  
5.4772...
nvecs(n: int, r: int, flipsign: bool = True) ndarray[source]

Compute the leading mode-n vectors of the pyttb.sptensor.

Computes the r leading eigenvectors of Sn*Sn.T (where Sn is the mode-n matricization/unfolding of a sparse tensor S), which provides information about the mode-n fibers. In two-dimensions, the r leading mode-1 vectors are the same as the r left singular vectors and the r leading mode-2 vectors are the same as the r right singular vectors. By default, this method computes the top r eigenvectors of Sn*Sn.T. The output product for sparse tensors is not formed, making this operation very efficient when the tensor is very sparse.

Parameters:
  • n – Mode to use for matricization.

  • r – Number of eigenvectors to compute and use.

  • flipsign – If True, make each column’s largest element positive.

Examples

Create a pyttb.sptensor:

>>> subs = np.array([[0, 0, 0], [0, 1, 1], [1, 0, 0]])
>>> vals = np.array([[1.0], [2.0], [3.0]])
>>> shape = (2, 2, 2)
>>> S = ttb.sptensor(subs, vals, shape)

Compute two mode-0 leading eigenvectors of S, making sign of largest element of each eigenvector positive (i.e., flipsign =True):

>>> S.nvecs(0, 2, flipsign=True)  
array([[-0.4718...,  0.8816...],
       [ 0.8816...,  0.4718...]])

Compute the same nvecs of S, but do not adjust the sign of the largest element of each eigenvector:

>>> S.nvecs(0, 2, flipsign=False)  
array([[ 0.4718..., -0.8816...],
       [-0.8816..., -0.4718...]])
ones() sptensor[source]

Replace nonzero values of the pyttb.sptensor with ones (1).

Examples

Create a pyttb.sptensor:

>>> subs = np.array([[0, 0, 0], [0, 1, 1], [1, 0, 0]])
>>> vals = np.array([[1.0], [2.0], [3.0]])
>>> shape = (2, 2, 2)
>>> S = ttb.sptensor(subs, vals, shape)
>>> S
sparse tensor of shape (2, 2, 2) with 3 nonzeros and order F
[0, 0, 0] = 1.0
[0, 1, 1] = 2.0
[1, 0, 0] = 3.0

Replace the nonzero values of S with the value 1:

>>> S.ones()
sparse tensor of shape (2, 2, 2) with 3 nonzeros and order F
[0, 0, 0] = 1.0
[0, 1, 1] = 1.0
[1, 0, 0] = 1.0
permute(order: int | float | Iterable[int] | Iterable[float] | ndarray) sptensor[source]

Permute the pyttb.sptensor dimensions.

The result is a new sparse tensor that has the same values, but the order of the subscripts needed to access any particular element are rearranged as specified by order.

Parameters:

order – New order of tensor dimensions.

Examples

Create a pyttb.sptensor:

>>> subs = np.array([[0, 0, 0], [0, 1, 1], [1, 0, 0]])
>>> vals = np.array([[1.0], [2.0], [3.0]])
>>> shape = (2, 2, 2)
>>> S = ttb.sptensor(subs, vals, shape)
>>> S
sparse tensor of shape (2, 2, 2) with 3 nonzeros and order F
[0, 0, 0] = 1.0
[0, 1, 1] = 2.0
[1, 0, 0] = 3.0

Permute the order of the dimensions by reversing them:

>>> S1 = S.permute(np.array((1, 0, 2)))
>>> S1
sparse tensor of shape (2, 2, 2) with 3 nonzeros and order F
[0, 0, 0] = 1.0
[1, 0, 1] = 2.0
[0, 1, 0] = 3.0
reshape(new_shape: int | Iterable[int], old_modes: ndarray | int | None = None) sptensor[source]

Reshape the pyttb.sptensor to the new_shape.

If old_modes is specified, reshape only those modes of the sparse tensor, moving newly reshaped modes to the end of the subscripts; otherwise use all modes. The product of the new shape must equal the product of the old shape.

Parameters:
  • new_shape – New shape.

  • old_modes – Modes used for reshaping.

Examples

Create a pyttb.sptensor from a pyttb.tensor:

>>> S = ttb.tensor(np.arange(9) + 1, shape=(1, 3, 3)).to_sptensor()
>>> S
sparse tensor of shape (1, 3, 3) with 9 nonzeros and order F
[0, 0, 0] = 1
[0, 1, 0] = 2
[0, 2, 0] = 3
[0, 0, 1] = 4
[0, 1, 1] = 5
[0, 2, 1] = 6
[0, 0, 2] = 7
[0, 1, 2] = 8
[0, 2, 2] = 9

Reshape to a 2-way pyttb.sptensor:

>>> S.reshape((1, 9))
sparse tensor of shape (1, 9) with 9 nonzeros and order F
[0, 0] = 1
[0, 1] = 2
[0, 2] = 3
[0, 3] = 4
[0, 4] = 5
[0, 5] = 6
[0, 6] = 7
[0, 7] = 8
[0, 8] = 9

Reshape the first two dimensions and move to the end of the subscripts. The first two subscripts are reshaped from (1,3) to (3,1) and moved after the remaining subscript (i.e., corresponding to mode 2).

>>> S.reshape(new_shape=(3, 1), old_modes=np.array((1, 0)))
sparse tensor of shape (3, 3, 1) with 9 nonzeros and order F
[0, 0, 0] = 1
[0, 1, 0] = 2
[0, 2, 0] = 3
[1, 0, 0] = 4
[1, 1, 0] = 5
[1, 2, 0] = 6
[2, 0, 0] = 7
[2, 1, 0] = 8
[2, 2, 0] = 9
scale(factor: ndarray | tensor | sptensor, dims: int | float | Iterable[int] | Iterable[float] | ndarray) sptensor[source]

Scale the pyttb.sptensor along specified dimensions.

Parameters:
  • factor – Scaling factor.

  • dims – Dimensions to scale.

Examples

Create a pyttb.sptensor from a pyttb.tensor:

>>> S = ttb.tensor(np.arange(9) + 1, shape=(1, 3, 3)).to_sptensor()
>>> S
sparse tensor of shape (1, 3, 3) with 9 nonzeros and order F
[0, 0, 0] = 1
[0, 1, 0] = 2
[0, 2, 0] = 3
[0, 0, 1] = 4
[0, 1, 1] = 5
[0, 2, 1] = 6
[0, 0, 2] = 7
[0, 1, 2] = 8
[0, 2, 2] = 9

Mode 2 is of length 3. Create a scaling factor array of length 3 and scale along mode 2:

>>> scaling_factor = np.array([1, 2, 3])
>>> S.scale(scaling_factor, np.array([2]))
sparse tensor of shape (1, 3, 3) with 9 nonzeros and order F
[0, 0, 0] = 1
[0, 1, 0] = 2
[0, 2, 0] = 3
[0, 0, 1] = 8
[0, 1, 1] = 10
[0, 2, 1] = 12
[0, 0, 2] = 21
[0, 1, 2] = 24
[0, 2, 2] = 27
spmatrix() coo_matrix[source]

Convert 2-way pyttb.sptensor to scipy.sparse.coo_matrix.

Examples

Create a 2-way pyttb.sptensor:

>>> S = ttb.tendiag([1, 2]).to_sptensor()
>>> S
sparse tensor of shape (2, 2) with 2 nonzeros and order F
[0, 0] = 1.0
[1, 1] = 2.0

Convert it to a scipy.sparse.coo_matrix:

>>> M = S.spmatrix()
>>> type(M)
<class 'scipy.sparse._coo.coo_matrix'>
>>> M.toarray()
array([[1., 0.],
       [0., 2.]])
squash(return_inverse: Literal[False]) pyttb.sptensor.sptensor[source]
squash(return_inverse: Literal[True]) tuple[pyttb.sptensor.sptensor, dict]
squash(return_inverse: bool = False) sptensor | tuple[sptensor, dict]

Remove empty slices from a pyttb.sptensor.

Parameters:

return_inverse – Return mapping from new tensor to old tensor subscripts.

Examples

Create a pyttb.sptensor with a few entries and squash empty slices:

>>> S = ttb.sptensor(shape=(10, 10, 10))
>>> S[0, 1, 2] = 1
>>> S[0, 1, 3] = 2
>>> S
sparse tensor of shape (10, 10, 10) with 2 nonzeros and order F
[0, 1, 2] = 1.0
[0, 1, 3] = 2.0
>>> S.squash()
sparse tensor of shape (2, 2, 2) with 2 nonzeros and order F
[0, 0, 0] = 1.0
[0, 0, 1] = 2.0

Squash and return the inverse subscript mapping, checking that the mapping in all dimensions is correct:

>>> S2, inverse = S.squash(True)
>>> for i in range(S.ndims):
...     np.array_equal(S.subs[:, i], inverse[i][S2.subs[:, i]])
True
True
True
squeeze() sptensor | float[source]

Remove singleton dimensions from the pyttb.sptensor.

Examples

Create a pyttb.sptensor with a single element and squeeze all the dimensions:

>>> S = ttb.sptensor(np.array([[0, 0, 0, 0, 0]]), np.array([[3.14]]))
>>> S.squeeze()
3.14

Create a pyttb.sptensor with and interior singleton dimension and squeeze it out:

>>> S = ttb.sptensor(np.array([[0, 0, 0], [1, 0, 1]]),
... np.array([[1.0], [2.0]]))
>>> S
sparse tensor of shape (2, 1, 2) with 2 nonzeros and order F
[0, 0, 0] = 1.0
[1, 0, 1] = 2.0
>>> S.squeeze()
sparse tensor of shape (2, 2) with 2 nonzeros and order F
[0, 0] = 1.0
[1, 1] = 2.0
subdims(region: Sequence[int | ndarray | slice]) ndarray[source]

Compute the locations of subscripts within a subdimension.

Finds the locations of the subscripts in the pyttb.sptensor that are within the range specified by region. For example, if region is [1, np.array([1,2]), np.array([1,2]]), then the locations of all elements of the sparse tensor that have a first subscript equal to 1, a second subscript equal to 1 or 2, and a third subscript equal to 1 or 2 are returned.

Parameters:

region – Subset of subscripts in which to find nonzero values.

Examples

Create a pyttb.sptensor:

>>> subs = np.array([[1, 1, 1], [1, 1, 3], [2, 2, 2], [2, 3, 2]])
>>> vals = np.array([[0.5], [1.5], [2.5], [3.5]])
>>> shape = (4, 4, 4)
>>> S = ttb.sptensor(subs, vals, shape)

Define a region with subscripts 1 in mode 0, 1 in mode 1, and either 1 or 3 in mode 2, then find the location of the subscripts of the S for that region:

>>> region = [1, 1, np.array([1, 3])]
>>> subs_loc = S.subdims(region)
>>> print(subs_loc)
[0 1]
>>> S.subs[subs_loc]
array([[1, 1, 1],
       [1, 1, 3]])

Use slice() to define part of the region. In this case, allow any subscript in mode 1:

>>> region = (2, slice(None, None, None), 2)
>>> subs_loc = S.subdims(region)
>>> print(subs_loc)
[2 3]
>>> S.subs[subs_loc]
array([[2, 2, 2],
       [2, 3, 2]])
to_sptenmat(rdims: ndarray | None = None, cdims: ndarray | None = None, cdims_cyclic: Literal['fc'] | Literal['bc'] | Literal['t'] | None = None) sptenmat[source]

Convert to pyttb.sptenmat.

Parameters:
  • rdims – Mapping of row indices.

  • cdims – Mapping of column indices.

  • cdims_cyclic – When only rdims is specified maps a single rdim to the rows and the remaining dimensions span the columns. fc (forward cyclic) in the order range(rdims,self.ndims()) followed by range(0, rdims). bc (backward cyclic) range(rdims-1, -1, -1) then range(self.ndims(), rdims, -1).

Notes

Forward cyclic is defined by Kiers [1] and backward cyclic is defined by De Lathauwer, De Moor, and Vandewalle [2].

References

Examples

Create a pyttb.sptensor:

>>> subs = np.array([[1, 2, 1], [1, 3, 1]])
>>> vals = np.array([[6], [7]])
>>> tshape = (4, 4, 4)
>>> S = ttb.sptensor(subs, vals, tshape)

Convert to a pyttb.sptenmat unwrapping around the first dimension using both implicit and explicit column dimension specification:

>>> ST1 = S.to_sptenmat(rdims=np.array([0]))
>>> ST2 = S.to_sptenmat(rdims=np.array([0]), cdims=np.array([1, 2]))
>>> ST1.isequal(ST2)
True

Convert using cyclic column ordering, where for the three mode case fc is the same result:

>>> ST3 = S.to_sptenmat(rdims=np.array([0]), cdims_cyclic="fc")
>>> ST3  
sptenmat corresponding to a sptensor of shape (4, 4, 4) with 2 nonzeros             and order F
rdims = [ 0 ] (modes of sptensor corresponding to rows)
cdims = [ 1, 2 ] (modes of sptensor corresponding to columns)
   [1, 6] = 6
   [1, 7] = 7

Backwards cyclic reverses the order:

>>> ST4 = S.to_sptenmat(rdims=np.array([0]), cdims_cyclic="bc")
>>> ST4  
sptenmat corresponding to a sptensor of shape (4, 4, 4) with 2 nonzeros             and order F
rdims = [ 0 ] (modes of sptensor corresponding to rows)
cdims = [ 2, 1 ] (modes of sptensor corresponding to columns)
    [1, 9] = 6
    [1, 13] = 7
to_tensor() tensor[source]

Convert to pyttb.tensor.

Same as pyttb.sptensor.full().

ttm(matrices: ndarray | Sequence[ndarray], dims: int | float | Iterable[int] | Iterable[float] | ndarray | None = None, exclude_dims: int | float | Iterable[int] | Iterable[float] | ndarray | None = None, transpose: bool = False) tensor | sptensor[source]

Multiplication of a pyttb.sptensor with a matrix.

Computes the n-mode product of the pyttb.sptensor with a matrix (i.e., array). Let n specify the dimension (or mode) along which the matrix should be multiplied. If the matrix has shape = (I,J), then the sparse tensor must have shape[n] = I. If the matrix has shape = (J,I), you can set transpose=True to multiply with the transpose of the matrix. The result has shape[n] = J.

Multiplication with more than one matrix is provided using a list of matrices and corresponding dimensions in the sparse tensor to use.

The dimensions of the sparse tensor with which to multiply can be provided as dims, or the dimensions to exclude from [0, …, self.ndims] can be specified using exclude_dims.

Parameters:
  • matrices – A matrix or list of matrices.

  • dims – Dimensions to multiply against.

  • exclude_dims – Use all dimensions but these.

  • transpose – Transpose matrices to be multiplied.

Examples

Create a pyttb.sptensor with a region of elements set to 1:

>>> S = ttb.sptensor(shape=(2, 2, 2, 2))
>>> S[:, 0:1, :, 0:1] = 1

Compute the product of S with multiple matrices of ones along the first two dimensions, transposing the matrices when multiplying:

>>> A = 2 * np.ones((2, 1))
>>> S.ttm([A, A], dims=[0, 1], transpose=True)
tensor of shape (1, 1, 2, 2) with order F
data[:, :, 0, 0] =
[[8.]]
data[:, :, 1, 0] =
[[8.]]
data[:, :, 0, 1] =
[[0.]]
data[:, :, 1, 1] =
[[0.]]

Compute sparse tensor matrix product specifying which two tensor dimensions to exclude in the multiplication:

>>> S.ttm([A, A], exclude_dims=[0, 1], transpose=True)
tensor of shape (2, 2, 1, 1) with order F
data[:, :, 0, 0] =
[[8. 0.]
 [8. 0.]]
ttv(vector: ndarray | Sequence[ndarray], dims: int | float | Iterable[int] | Iterable[float] | ndarray | None = None, exclude_dims: int | float | Iterable[int] | Iterable[float] | ndarray | None = None) sptensor | tensor | float[source]

Multiplication of the pyttb.sptensor with a vector.

Computes the n-mode product of the pyttb.sptensor with a vector. Let n specify the dimension (or mode) along which the vector should be multiplied. If the vector has shape = (I,), then the sparse tensor must have shape[n] = I. The result has one less dimension, as dimension n is removed in the multiplication.

Multiplication with more than one vector is provided using a list of vectors and corresponding dimensions in the sparse tensor to use.

The dimensions of the sparse tensor with which to multiply can be provided as dims, or the dimensions to exclude from [0, …, self.ndims] can be specified using exclude_dims.

Parameters:
  • vector – Vector or vectors to multiply by.

  • dims – Dimensions to multiply against.

  • exclude_dims – Use all dimensions but these.

Examples

Create a 2-way pyttb.sptensor that is relatively dense:

>>> subs = np.array([[0, 0, 0], [0, 1, 1], [1, 0, 0], [1, 1, 0]])
>>> vals = np.array([[1.0], [2.0], [3.0], [4.0]])
>>> shape = (2, 2, 2)
>>> S = ttb.sptensor(subs, vals, shape)
>>> S
sparse tensor of shape (2, 2, 2) with 4 nonzeros and order F
[0, 0, 0] = 1.0
[0, 1, 1] = 2.0
[1, 0, 0] = 3.0
[1, 1, 0] = 4.0

Compute the product of S with a vector of ones across mode 0. The result is a pyttb.tensor:

>>> S.ttv(np.ones(2), 0)
tensor of shape (2, 2) with order F
data[:, :] =
[[4. 0.]
 [4. 2.]]

Create a 3-way pyttb.sptensor that is more sparse:

>>> subs = np.array([[0, 0, 0], [0, 1, 0], [1, 0, 1]])
>>> vals = np.array([[1.0], [2.0], [3.0]])
>>> shape = (2, 2, 2)
>>> S1 = ttb.sptensor(subs, vals, shape)

Compute the product of S1 with a vector of ones across mode 1. The result is a pyttb.sptensor:

>>> S1.ttv(np.ones(2), 1)
sparse tensor of shape (2, 2) with 2 nonzeros and order F
[0, 0] = 3.0
[1, 1] = 3.0

Compute the product of S1 with multiple vectors across all dimensions. When all dimensions will be included in the product, dims does not need to be specified. The result is a scalar value:

>>> vectors = [(i + 1) * np.ones(2) for i in range(len(S1.shape))]
>>> vectors
[array([1., 1.]), array([2., 2.]), array([3., 3.])]
>>> S1.ttv(vectors)
36.0
__add__(other)[source]

Binary addition operator (+).

Parameters:

other – Object to add to the sparse tensor.

Examples

Add a pyttb.sptensor to itself, returning a sparse tensor:

>>> S = ttb.sptensor(shape=(2, 2, 2))
>>> S[1, 1, 1] = 1.0
>>> S + S
sparse tensor of shape (2, 2, 2) with 1 nonzeros and order F
[1, 1, 1] = 2.0

Add a scalar value, returning a dense tensor:

>>> S + 1
tensor of shape (2, 2, 2) with order F
data[:, :, 0] =
[[1. 1.]
 [1. 1.]]
data[:, :, 1] =
[[1. 1.]
 [1. 2.]]
__eq__(other)[source]

Element-wise equal operator (==).

Parameters:

other – Other object to compare with.

Examples

Compare the pyttb.sptensor to itself, returning all True values:

>>> S = ttb.sptensor(shape=(2, 2, 2))
>>> S[1, 1, 1] = 1.0
>>> S[0, 0, 1] = 2.0
>>> S == S
sparse tensor of shape (2, 2, 2) with 8 nonzeros and order F
[0, 0, 0] = 1.0
[0, 1, 0] = 1.0
[0, 1, 1] = 1.0
[1, 0, 0] = 1.0
[1, 0, 1] = 1.0
[1, 1, 0] = 1.0
[1, 1, 1] = 1.0
[0, 0, 1] = 1.0

Compare with a scalar value, returning only a single True value:

>>> S == 1
sparse tensor of shape (2, 2, 2) with 1 nonzeros and order F
[1, 1, 1] = 1.0
__ge__(other)[source]

Greater than or equal operator (>=).

Parameters:

other – Object to compare with.

Examples

Compare a pyttb.sptensor with itself:

>>> S = ttb.sptensor(shape=(2, 2, 2))
>>> S[1, 1, 1] = 1.0
>>> S >= S
sparse tensor of shape (2, 2, 2) with 8 nonzeros and order F
[1, 1, 1] = 1.0
[0, 0, 0] = 1.0
[0, 0, 1] = 1.0
[0, 1, 0] = 1.0
[0, 1, 1] = 1.0
[1, 0, 0] = 1.0
[1, 0, 1] = 1.0
[1, 1, 0] = 1.0

Compare with a scalar:

>>> S >= 1
sparse tensor of shape (2, 2, 2) with 1 nonzeros and order F
[1, 1, 1] = 1.0
__getitem__(item)[source]

Subscripted reference for the pyttb.sptensor.

We can extract elements or subtensors from a sparse tensor in the following ways.

Case 1a: y = S[I1,I2,…,In], where each I is an subscript, returns a scalar.

Case 1b: Y = S[R1,R2,…,Rn], where one or more R is a range and the rest are subsctiprs, returns a sparse tensor. The elements are renumbered here as appropriate.

Case 2a: V = S[M] where `M is a p x n array of subscripts, returns a vector of p values.

Case 2b: V = S[I] where I is a set of p linear subscripts, returns a vector of p values.

Any ambiguity results in executing the first valid case. This is particularly an issue if self.ndims == 1.

Examples

Create a 3-way pyttb.sptensor:

>>> subs = np.array([[3, 3, 3], [1, 1, 0], [1, 2, 1]])
>>> vals = np.array([[3], [5], [1]])
>>> shape = (4, 4, 4)
>>> S = ttb.sptensor(subs, vals, shape)

Use a single subscript (Case 1a):

>>> print(S[1, 2, 1])
1

Use a range of subscripts (Case 1b):

>>> S[3, 3, :]
sparse tensor of shape (4,) with 1 nonzeros and order F
[3] = 3

Use an array of subscripts (Case 2a):

>>> M = np.array([[1, 1, 0], [1, 1, 1]])
>>> print(S[M])
[[5]
 [0]]

Use linear subscripting, including negative subscript for offsets from the end of the linear subscripts into the sparse tensor data (Case 2b):

>>> print(S[[5, -1]])
[[5]
 [3]]
__gt__(other)[source]

Greater than operator (>).

Parameters:

other – Object to compare with.

Examples

Compare a pyttb.sptensor with itself:

>>> S = ttb.sptensor(shape=(2, 2, 2))
>>> S[1, 1, 1] = 1.0
>>> S > S
empty sparse tensor of shape (2, 2, 2) with order F

Compare with a scalar:

>>> S > 0
sparse tensor of shape (2, 2, 2) with 1 nonzeros and order F
[1, 1, 1] = 1.0
__le__(other)[source]

Less than or equal operator (<=).

Parameters:

other – Object to compare with.

Examples

Compare a pyttb.sptensor with itself:

>>> S = ttb.sptensor(shape=(2, 2, 2))
>>> S[1, 1, 1] = 1.0
>>> S <= S
sparse tensor of shape (2, 2, 2) with 8 nonzeros and order F
[1, 1, 1] = 1.0
[0, 0, 0] = 1.0
[0, 0, 1] = 1.0
[0, 1, 0] = 1.0
[0, 1, 1] = 1.0
[1, 0, 0] = 1.0
[1, 0, 1] = 1.0
[1, 1, 0] = 1.0

Compare with a scalar:

>>> S <= -1
empty sparse tensor of shape (2, 2, 2) with order F
__lt__(other)[source]

Less than operator (<).

Parameters:

other – Object to compare with.

Examples

Compare a pyttb.sptensor with itself:

>>> S = ttb.sptensor(shape=(2, 2, 2))
>>> S[1, 1, 1] = 1.0
>>> S < S
empty sparse tensor of shape (2, 2, 2) with order F

Compare with a scalar:

>>> S < 1
sparse tensor of shape (2, 2, 2) with 7 nonzeros and order F
[0, 0, 0] = 1.0
[0, 0, 1] = 1.0
[0, 1, 0] = 1.0
[0, 1, 1] = 1.0
[1, 0, 0] = 1.0
[1, 0, 1] = 1.0
[1, 1, 0] = 1.0
__mul__(other)[source]

Element-wise multiplication operator (*).

Parameters:

other – Object to multiply with the sparse tensor.

Examples

Multiply a pyttb.sptensor by a scalar:

>>> S = ttb.sptensor(shape=(2, 2, 2))
>>> S[1, 1, 1] = 1.0
>>> S * 3
sparse tensor of shape (2, 2, 2) with 1 nonzeros and order F
[1, 1, 1] = 3.0

Multiply two sparse tensors with no overlap in subscripts of nonzeros, resulting in an empty sparse tensor:

>>> S2 = ttb.sptensor(shape=(2, 2, 2))
>>> S2[1, 0, 0] = 1.0
>>> S * S2
empty sparse tensor of shape (2, 2, 2) with order F
__ne__(other)[source]

Element-wise not equal operator (!=).

Parameters:

other – Other object to compare with.

Examples

Compare a pyttb.sptensor to itself, returning no True values:

>>> S = ttb.sptensor(shape=(2, 2, 2))
>>> S[1, 1, 1] = 1.0
>>> S != S
empty sparse tensor of shape (2, 2, 2) with order F

Compare with a scalar value:

>>> S != 1
sparse tensor of shape (2, 2, 2) with 7 nonzeros and order F
[0, 0, 0] = 1.0
[0, 0, 1] = 1.0
[0, 1, 0] = 1.0
[0, 1, 1] = 1.0
[1, 0, 0] = 1.0
[1, 0, 1] = 1.0
[1, 1, 0] = 1.0
__neg__()[source]

Unary minus operator (-).

Examples

Create a pyttb.sptensor:

>>> S = ttb.sptensor(shape=(2, 2, 2))
>>> S[1, 1, 1] = 1
>>> S
sparse tensor of shape (2, 2, 2) with 1 nonzeros and order F
[1, 1, 1] = 1.0

Apply the - operator:

>>> -S
sparse tensor of shape (2, 2, 2) with 1 nonzeros and order F
[1, 1, 1] = -1.0
__pos__()[source]

Unary plus operator (+).

Examples

Create a pyttb.sptensor:

>>> S = ttb.sptensor(shape=(2, 2, 2))
>>> S[1, 1, 1] = 1
>>> S
sparse tensor of shape (2, 2, 2) with 1 nonzeros and order F
[1, 1, 1] = 1.0

Apply the + operator:

>>> +S
sparse tensor of shape (2, 2, 2) with 1 nonzeros and order F
[1, 1, 1] = 1.0
__hash__ = None
__radd__(other)[source]

Right binary addition operator (+).

Parameters:

other – Object to add to the sparse tensor.

Examples

Add a scalar value, returning a dense tensor:

>>> S = ttb.sptensor(shape=(2, 2, 2))
>>> S[1, 1, 1] = 1.0
>>> 1 + S
tensor of shape (2, 2, 2) with order F
data[:, :, 0] =
[[1. 1.]
 [1. 1.]]
data[:, :, 1] =
[[1. 1.]
 [1. 2.]]
__repr__()[source]

Return string representation of a pyttb.sptensor.

Examples

Create a pyttb.sptensor and print it as a string:

>>> S = ttb.sptensor(shape=(2, 2, 2))
>>> S[:, :, :] = 1.0
>>> print(S)
sparse tensor of shape (2, 2, 2) with 8 nonzeros and order F
[0, 0, 0] = 1.0
[0, 0, 1] = 1.0
[0, 1, 0] = 1.0
[0, 1, 1] = 1.0
[1, 0, 0] = 1.0
[1, 0, 1] = 1.0
[1, 1, 0] = 1.0
[1, 1, 1] = 1.0
__rmul__(other)[source]

Element-wise right multiplication operator (*).

Parameters:

other – Object to multiple with sparse tensor.

Examples

Multiple scalar by a pyttb.sptensor:

>>> S = ttb.sptensor(shape=(2, 2, 2))
>>> S[1, 1, 1] = 1.0
>>> 3 * S
sparse tensor of shape (2, 2, 2) with 1 nonzeros and order F
[1, 1, 1] = 3.0
__rtruediv__(other)[source]

Element-wise right division operator (/).

Parameters:

other – Object to divide sparse tensor by.

Examples

Divide a scalar by a pyttb.sptensor:

>>> S = ttb.sptensor(shape=(2, 2, 2))
>>> S[:, :, :] = 2.0
>>> 1 / S
tensor of shape (2, 2, 2) with order F
data[:, :, 0] =
[[0.5 0.5]
 [0.5 0.5]]
data[:, :, 1] =
[[0.5 0.5]
 [0.5 0.5]]
__setitem__(key, value)[source]

Subscripted assignment for the pyttb.sptensor.

We can assign elements to a sparse tensor in the following ways.

Case 1: S[R1,R2,…,Rn] = Y, in which case we replace the rectangular subtensor (or single element) specified by the ranges R1,…,`Rn` with Y. The right-hand-side can be a scalar or an sparse tensor.

Case 2: S[M] = V, where M is a p x n array of subscripts and V is a scalar value or a vector containing p values.

Assignment using linear subscripting is not supported for sparse tensors.

Examples

Create a 3-way pyttb.sptensor:

>>> S = ttb.sptensor(shape=(3, 4, 5))

Set a single element using subscripts or a tuple:

>>> S[0, 0, 0] = 1
>>> S[(0, 0, 0)] = 1
>>> S
sparse tensor of shape (3, 4, 5) with 1 nonzeros and order F
[0, 0, 0] = 1.0
>>> S
sparse tensor of shape (3, 4, 5) with 1 nonzeros and order F
[0, 0, 0] = 1.0

Set a range of elements using a single value:

>>> S[0, 0, 1:3] = 2
>>> S
sparse tensor of shape (3, 4, 5) with 3 nonzeros and order F
[0, 0, 0] = 1.0
[0, 0, 1] = 2.0
[0, 0, 2] = 2.0

Set a range of elements using a pyttb.sptensor:

>>> S[0:1, 1:3, 3:4] = 3 * ttb.tenones((1, 2, 1)).to_sptensor()
>>> S
sparse tensor of shape (3, 4, 5) with 5 nonzeros and order F
[0, 0, 0] = 1.0
[0, 0, 1] = 2.0
[0, 0, 2] = 2.0
[0, 1, 3] = 3.0
[0, 2, 3] = 3.0

Grow the sparse tensor by assigning an element with a subscript outside the current shape:

>>> S[3, 4, 5] = 4
>>> S
sparse tensor of shape (4, 5, 6) with 6 nonzeros and order F
[0, 0, 0] = 1.0
[0, 0, 1] = 2.0
[0, 0, 2] = 2.0
[0, 1, 3] = 3.0
[0, 2, 3] = 3.0
[3, 4, 5] = 4.0

Assign one or more values using an array of subscripts and a vector of values:

>>> S[S.subs] = 5 * np.ones((S.vals.shape[0], 1))
>>> S
sparse tensor of shape (4, 5, 6) with 6 nonzeros and order F
[0, 0, 0] = 5.0
[0, 0, 1] = 5.0
[0, 0, 2] = 5.0
[0, 1, 3] = 5.0
[0, 2, 3] = 5.0
[3, 4, 5] = 5.0

Note regarding singleton dimensions: It is not possible to do, for instance, S[1,1:10,1:10] = ttb.sptenrand((1,10,10),nonzeros=5). However, it is okay to do S[1,1:10,1:10] = ttb.sptenrand((1,10,10),nonzeros=5).squeeze().

__str__()

Return string representation of a pyttb.sptensor.

Examples

Create a pyttb.sptensor and print it as a string:

>>> S = ttb.sptensor(shape=(2, 2, 2))
>>> S[:, :, :] = 1.0
>>> print(S)
sparse tensor of shape (2, 2, 2) with 8 nonzeros and order F
[0, 0, 0] = 1.0
[0, 0, 1] = 1.0
[0, 1, 0] = 1.0
[0, 1, 1] = 1.0
[1, 0, 0] = 1.0
[1, 0, 1] = 1.0
[1, 1, 0] = 1.0
[1, 1, 1] = 1.0
__sub__(other)[source]

Binary subtraction operator (-).

Parameters:

other – Object to subtract from the sparse tensor.

Examples

Subtract a pyttb.sptensor from itself, returning a sparse tensor:

>>> S = ttb.sptensor(shape=(2, 2, 2))
>>> S[1, 1, 1] = 1.0
>>> S - S
empty sparse tensor of shape (2, 2, 2) with order F

Subtract a scalar value, returning a dense tensor:

>>> S - 1
tensor of shape (2, 2, 2) with order F
data[:, :, 0] =
[[-1. -1.]
 [-1. -1.]]
data[:, :, 1] =
[[-1. -1.]
 [-1.  0.]]
__truediv__(other)[source]

Element-wise left division operator (/).

Comparisons with empty tensors raise an exception.

Parameters:

other – Object to divide from the sparse tensor.

Examples

Divide a pyttb.sptensor by a pyttb.sptensor:

>>> S = ttb.sptensor(shape=(2, 2, 2))
>>> S[1, 1, 1] = 2.0
>>> S2 = ttb.sptensor(shape=(2, 2, 2))
>>> S2[1, 1, 1] = 4.0
>>> S / S2
sparse tensor of shape (2, 2, 2) with 8 nonzeros and order F
[1, 1, 1] = 0.5
[0, 0, 0] = nan
[0, 0, 1] = nan
[0, 1, 0] = nan
[0, 1, 1] = nan
[1, 0, 0] = nan
[1, 0, 1] = nan
[1, 1, 0] = nan

Divide by a scalar:

>>> S / 3  
sparse tensor of shape (2, 2, 2) with 1 nonzeros and order F
[1, 1, 1] = 0.66666...
pyttb.sptendiag(elements: int | float | Iterable[int] | Iterable[float] | ndarray, shape: int | Iterable[int] | None = None) sptensor[source]

Create a pyttb.sptensor with elements along the super diagonal.

If provided shape is too small the sparse tensor will be enlarged to accommodate.

Parameters:
  • elements – Elements to set along the diagonal.

  • shape – Shape of the resulting sparse tensor.

Examples

Create a pyttb.sptensor by specifying the super diagonal with a 1-D array that has 3 elements, which will create a 3x3x3 sparse tensor:

>>> shape = (3,)
>>> values = np.ones(shape)
>>> S = ttb.sptendiag(values)

Create a 3x3x3 pyttb.sptensor, specifying the correct shape, and verify that it is equal to S:

>>> S2 = ttb.sptendiag(values, (3, 3, 3))
>>> S.isequal(S2)
True
pyttb.sptenrand(shape: int | Iterable[int], density: float | None = None, nonzeros: float | None = None) sptensor[source]

Create a pyttb.sptensor with random entries and indices.

Entries drawn from a uniform distribution on the unit interval and indices selected using a uniform distribution. You can specify the density or number of nonzeros in the resulting sparse tensor but not both.

Parameters:
  • shape – Shape of resulting sparse tensor.

  • density – Density of resulting sparse tensor.

  • nonzeros – Number of nonzero entries in resulting sparse tensor.

Examples

Create a pyttb.sptensor, specifying the number of nonzeros:

>>> S = ttb.sptenrand((2, 2), nonzeros=1)

Create a pyttb.sptensor, specifying the density of nonzeros:

>>> S2 = ttb.sptenrand((2, 2), density=0.25)