Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
5 changes: 4 additions & 1 deletion docs/make.jl
Original file line number Diff line number Diff line change
Expand Up @@ -14,7 +14,10 @@ pages = [
"Home" => "index.md",
"Manual" => [
"man/intro.md", "man/tutorial.md",
"man/spaces.md", "man/sectors.md", "man/tensors.md",
"man/spaces.md", "man/symmetries.md",
"man/sectors.md", "man/gradedspaces.md",
"man/fusiontrees.md", "man/tensors.md",
"man/tensormanipulations.md",
],
"Library" => [
"lib/sectors.md", "lib/fusiontrees.md",
Expand Down
496 changes: 245 additions & 251 deletions docs/src/appendix/categories.md

Large diffs are not rendered by default.

147 changes: 70 additions & 77 deletions docs/src/appendix/symmetric_tutorial.md

Large diffs are not rendered by default.

22 changes: 11 additions & 11 deletions docs/src/index.md
Original file line number Diff line number Diff line change
Expand Up @@ -19,23 +19,23 @@ from [TensorOperations.jl](https://github.com/QuantumKitHub/TensorOperations.jl)
Currently, most effort is oriented towards tensors as they appear in the context of quantum
many-body physics and in particular the field of tensor networks. Such tensors often have
large dimensions and take on a specific structure when symmetries are present. By employing
concepts from category theory, we can represent and manipulate tensors with a large
variety of symmetries, including abelian and non-abelian symmetries, fermionic statistics,
as well as generalized (a.k.a. non-invertible or anyonic) symmetries.
concepts from category theory, we can represent and manipulate tensors with a large variety
of symmetries, including abelian and non-abelian symmetries, fermionic statistics, as well
as generalized (a.k.a. non-invertible or anyonic) symmetries.

At the same time, TensorKit.jl focusses on computational efficiency and performance. The
underlying storage of a tensor's data can be any `DenseArray`. When the data is stored
in main memory (corresponding to `Array`), multiple CPUs can be leveraged as many
operations come with multithreaded implementations, either by distributing the different
blocks in case of a structured tensor (i.e. with symmetries) or by using multithreading
provided by the package [Strided.jl](https://github.com/Jutho/Strided.jl). Support for
storing and manipulating tensors on NVidia and AMD GPUs is currently being developed,
whereas support for distributed arrays is planned for the future.
underlying storage of a tensor's data can be any `DenseArray`. When the data is stored in
main memory (corresponding to `Array`), multiple CPUs can be leveraged as many operations
come with multithreaded implementations, either by distributing the different blocks in case
of a structured tensor (i.e. with symmetries) or by using multithreading provided by the
package [Strided.jl](https://github.com/Jutho/Strided.jl). Support for storing and
manipulating tensors on NVidia and AMD GPUs is currently being developed, whereas support
for distributed arrays is planned for the future.

## Contents of the manual

```@contents
Pages = ["man/intro.md", "man/spaces.md", "man/sectors.md", "man/tensors.md"]
Pages = ["man/intro.md", "man/spaces.md", "man/symmetries.md", "man/sectors.md", "man/gradedspaces.md", "man/fusiontrees.md", "man/tensors.md", "man/tensormanipulations.md"]
Depth = 2
```

Expand Down
4 changes: 2 additions & 2 deletions docs/src/lib/fusiontrees.md
Original file line number Diff line number Diff line change
Expand Up @@ -45,8 +45,8 @@ TensorKit.cycleanticlockwise
```

Finally, these are used to define large manipulations of fusion-splitting tree pairs, which
are then used in the index manipulation of `AbstractTensorMap` objects. The following methods
defined on fusion splitting tree pairs have an associated definition for tensors.
are then used in the index manipulation of `AbstractTensorMap` objects. The following
methods defined on fusion splitting tree pairs have an associated definition for tensors.
```@docs
repartition(::FusionTree{I,N₁}, ::FusionTree{I,N₂}, ::Int) where {I<:Sector,N₁,N₂}
transpose(::FusionTree{I}, ::FusionTree{I}, ::IndexTuple{N₁}, ::IndexTuple{N₂}) where {I<:Sector,N₁,N₂}
Expand Down
35 changes: 21 additions & 14 deletions docs/src/lib/sectors.md
Original file line number Diff line number Diff line change
Expand Up @@ -40,8 +40,8 @@ Several more concrete sector types can be found in other packages such as
[CategoryData.jl](https://github.com/QuantumKitHub/CategoryData.jl),
[QWignerSymbols.jl](https://github.com/lkdvos/QWignerSymbols.jl), ...:

Some of these types are parameterized by a type parameter that represents a group.
We therefore also provide a number of types to represent groups:
Some of these types are parameterized by a type parameter that represents a group. We
therefore also provide a number of types to represent groups:

```@docs
TensorKitSectors.Group
Expand All @@ -54,17 +54,17 @@ TensorKitSectors.Dihedral
TensorKitSectors.ProductGroup
```

The following types are used to characterise different properties of the different types
of sectors:
The following types are used to characterise different properties of the different types of
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Suggested change
The following types are used to characterise different properties of the different types of
The following types are used to characterize different properties of the different types of

Since American English is preferred in the docs

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Somehow I cannot commit this suggestion directly so I'll have to change it manually.

sectors:

```@docs
FusionStyle
BraidingStyle
UnitStyle
```

Finally, the following auxiliary types are defined to facilitate the implementation
of some of the methods on sectors:
Finally, the following auxiliary types are defined to facilitate the implementation of some
of the methods on sectors:

```@docs
TensorKitSectors.SectorValues
Expand All @@ -73,8 +73,8 @@ TensorKitSectors.SectorProductIterator

## Useful constants

The following constants are defined to facilitate obtaining the type associated
with the group elements or the irreducible representations of a given group:
The following constants are defined to facilitate obtaining the type associated with the
group elements or the irreducible representations of a given group:

```@docs
Irrep
Expand All @@ -83,8 +83,8 @@ GroupElement

## Methods for characterizing and manipulating `Sector` objects

The following methods can be used to obtain properties such as topological data
of sector objects, or to manipulate them or create related sectors:
The following methods can be used to obtain properties such as topological data of sector
objects, or to manipulate them or create related sectors:

```@docs
unit
Expand All @@ -107,8 +107,8 @@ TensorKitSectors.sectorscalartype
deligneproduct(::Sector, ::Sector)
```

We have also the following methods that are specific to certain types of sectors
and serve as accessors to their fields:
We have also the following methods that are specific to certain types of sectors and serve
as accessors to their fields:

```@docs
charge
Expand All @@ -121,8 +121,15 @@ Furthermore, we also have one specific method acting on groups, represented as t
×
```

Because we sometimes want to customize the string representation of our sector types,
we also have the following method:
Mapping between sectors and linear indices is only used for sectors `I` for which
`Base.IteratorSize(values(I)) == HasLength()`. In that case, we map an index `i` to a sector
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Is this true? I can call e.g. values(SU2Irrep)[3] and it gives SU2Irrep(1)

Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

The original reason for that method is that in the spaces, instead of a Dict{Sector,Int} for the degeneracies we are storing a NTuple{N, Int} and using direct indexing. This requires a finite and compile-time known number of different sectors.
I would have to double check, but I don't think we are really using that function for anything else right now.

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

But yes, it is true. There is a default getindex(::SectorValues{I}, i) that really just runs the values(I) iterator until it reaches the ith element. The same with findindex(::SectorValues{I}, c::I) that runs the iterator and counts how long it takes before the requested sector c is reached.

`c` via `c = getindex(values(I), i)`, and provide an inverse mapping
```@docs
TensorKitSectors.findindex
```

Because we sometimes want to customize the string representation of our sector types, we
also have the following method:

```@docs
TensorKitSectors.type_repr
Expand Down
12 changes: 6 additions & 6 deletions docs/src/lib/spaces.md
Original file line number Diff line number Diff line change
Expand Up @@ -21,8 +21,8 @@ ProductSpace
HomSpace
```

together with the following specific type for encoding the inner product structure of
a space:
together with the following specific type for encoding the inner product structure of a
space:

```@docs
InnerProductStyle
Expand Down Expand Up @@ -110,16 +110,16 @@ isepimorphic
isisomorphic
```

Inserting trivial space factors or removing such factors for `ProductSpace` instances
can be done with the following methods.
Inserting trivial space factors or removing such factors for `ProductSpace` instances can be
done with the following methods.
```@docs
insertleftunit(::ProductSpace, ::Val{i}) where {i}
insertrightunit(::ProductSpace, ::Val{i}) where {i}
removeunit(::ProductSpace, ::Val{i}) where {i}
```

There are also specific methods for `HomSpace` instances, that are used in determining
the resuling `HomSpace` after applying certain tensor operations.
There are also specific methods for `HomSpace` instances, that are used in determining the
resuling `HomSpace` after applying certain tensor operations.
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Suggested change
resuling `HomSpace` after applying certain tensor operations.
resulting `HomSpace` after applying certain tensor operations.

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This suggestion I can also not commit directly. Very strange.


```@docs
flip(W::HomSpace{S}, I) where {S}
Expand Down
54 changes: 29 additions & 25 deletions docs/src/lib/tensors.md
Original file line number Diff line number Diff line change
Expand Up @@ -38,11 +38,11 @@ TensorMap{T}(::UndefInitializer, V::TensorMapSpace)
```

The resulting object can then be filled with data using the `setindex!` method as discussed
below, using functions such as `VectorInterface.zerovector!`, `rand!` or `fill!`, or it can
be used as an output argument in one of the many methods that accept output arguments, or
in an `@tensor output[...] = ...` expression.
below, using functions such as `VectorInterface.zerovector!`, `rand!` or `fill!`, or it can
be used as an output argument in one of the many methods that accept output arguments, or in
an `@tensor output[...] = ...` expression.

Alternatively, a `TensorMap` can be constructed by specifying its data, codmain and domain
Alternatively, a `TensorMap` can be constructed by specifying its data, codomain and domain
in one of the following ways:
```@docs
TensorMap(data::AbstractDict{<:Sector,<:AbstractMatrix}, V::TensorMapSpace)
Expand Down Expand Up @@ -98,8 +98,9 @@ domainind
allind
```

In `TensorMap` instances, all data is gathered in a single `AbstractVector`, which has an internal structure into blocks associated to total coupled charge, within which live subblocks
associated with the different possible fusion-splitting tree pairs.
In `TensorMap` instances, all data is gathered in a single `AbstractVector`, which has an
internal structure into blocks associated to total coupled charge, within which live
subblocks associated with the different possible fusion-splitting tree pairs.

To obtain information about the structure of the data, you can use:
```@docs
Expand All @@ -110,7 +111,8 @@ hasblock(::AbstractTensorMap, ::Sector)
fusiontrees(t::AbstractTensorMap)
```

Data can be accessed (and modified) in a number of ways. To access the full matrix block associated with the coupled charges, you can use:
Data can be accessed (and modified) in a number of ways. To access the full matrix block
associated with the coupled charges, you can use:
```@docs
block
blocks
Expand All @@ -128,7 +130,7 @@ Base.getindex(::AbstractTensorMap, ::FusionTree, ::FusionTree)
Base.setindex!(::AbstractTensorMap, ::Any, ::FusionTree, ::FusionTree)
```

For a tensor `t` with `FusionType(sectortype(t)) isa UniqueFusion`, fusion trees are
For a tensor `t` with `FusionType(sectortype(t)) isa UniqueFusion`, fusion trees are
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Suggested change
For a tensor `t` with `FusionType(sectortype(t)) isa UniqueFusion`, fusion trees are
For a tensor `t` with `FusionStyle(sectortype(t)) isa UniqueFusion`, fusion trees are

completely determined by the outcoming sectors, and the data can be accessed in a more
straightforward way:
```@docs
Expand All @@ -155,25 +157,25 @@ Random.randexp!
The operations that can be performed on an `AbstractTensorMap` can be organized into the
following categories:

* *vector operations*: these do not change the `space` or index strucure of a tensor and
can be straightforwardly implemented on on the full data. All the methods described in
* *vector operations*: these do not change the `space` or index strucure of a tensor and can
be straightforwardly implemented on on the full data. All the methods described in
Comment on lines +160 to +161
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Suggested change
* *vector operations*: these do not change the `space` or index strucure of a tensor and can
be straightforwardly implemented on on the full data. All the methods described in
* *vector operations*: these do not change the `space` or index structure of a tensor and can
be straightforwardly implemented on the full data. All the methods described in

[VectorInterface.jl](https://github.com/Jutho/VectorInterface.jl) are supported. For
compatibility reasons, we also provide implementations for equivalent methods from
LinearAlgebra.jl, such as `axpy!`, `axpby!`.

* *index manipulations*: these change (permute) the index structure of a tensor, which
affects the data in a way that is fully determined by the categorical data of the
`sectortype` of the tensor.

* *(planar) contractions* and *(planar) traces* (i.e., contractions with identity tensors).
Tensor contractions correspond to a combination of some index manipulations followed by
a composition or multiplication of the tensors in their role as linear maps.
Tensor contractions are however of such important and frequency that they require a
dedicated implementation.
Tensor contractions correspond to a combination of some index manipulations followed by a
composition or multiplication of the tensors in their role as linear maps. Tensor
contractions are however of such important and frequency that they require a dedicated
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Suggested change
contractions are however of such important and frequency that they require a dedicated
contractions are however of such importance and frequency that they require a dedicated

implementation.

* *tensor factorisations*, which relies on their identification of tensors with linear maps
between tensor spaces. The factorisations are applied as ordinary matrix factorisations
to the matrix blocks associated with the coupled charges.
between tensor spaces. The factorisations are applied as ordinary matrix factorisations to
the matrix blocks associated with the coupled charges.
Comment on lines +177 to +178
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Suggested change
between tensor spaces. The factorisations are applied as ordinary matrix factorisations to
the matrix blocks associated with the coupled charges.
between tensor spaces. The factorizations are applied as ordinary matrix factorizations to
the matrix blocks associated with the coupled charges.

There's another "factorisation" in the line above


### Index manipulations

Expand Down Expand Up @@ -220,20 +222,22 @@ contract!

## `TensorMap` factorizations

The factorisation methods are powered by [MatrixAlgebraKit.jl](https://github.com/QuantumKitHub/MatrixAlgebraKit.jl)
and all follow the same strategy. The idea is that the `TensorMap` is interpreted as a linear
map based on the current partition of indices between `domain` and `codomain`, and then the
entire range of MatrixAlgebraKit functions can be called.
Factorizing a tensor according to a different partition of the indices is possible
by prepending the factorization step with an explicit call to [`permute`](@ref) or [`transpose`](@ref).
The factorisation methods are powered by
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Suggested change
The factorisation methods are powered by
The factorization methods are powered by

[MatrixAlgebraKit.jl](https://github.com/QuantumKitHub/MatrixAlgebraKit.jl) and all follow
the same strategy. The idea is that the `TensorMap` is interpreted as a linear map based on
the current partition of indices between `domain` and `codomain`, and then the entire range
of MatrixAlgebraKit functions can be called. Factorizing a tensor according to a different
partition of the indices is possible by prepending the factorization step with an explicit
call to [`permute`](@ref) or [`transpose`](@ref).

For the full list of factorizations, see [Decompositions](@extref MatrixAlgebraKit).

Additionally, it is possible to obtain truncated versions of some of these factorizations
through the [`MatrixAlgebraKit.TruncationStrategy`](@ref) objects.

The exact truncation strategy can be controlled through the strategies defined in [Truncations](@extref MatrixAlgebraKit),
but for `TensorMap`s there is also the special-purpose scheme:
The exact truncation strategy can be controlled through the strategies defined in
[Truncations](@extref MatrixAlgebraKit), but for `TensorMap`s there is also the
special-purpose scheme:

```@docs
truncspace
Expand Down
Loading
Loading