Tensor Categories

Magma allows tensors and tensor spaces to change categories. Unless a user specifies otherwise, all tensors are assigned a category that is natural to the method by which it was created. For example a tensor created from an algebra will be assigned an algebra category, whereas a tensor created by structure constants will be assigned the Albert homotopism category [Alb42]. Tensor categories influence the behavior of commands such as kernels and images as well as the algebraic invariants such as derivation algebras of a tensor.

Our conventions follow [Wil13]. In particular, given a tensor T framed by [Uν, ..., U0] then a tensor category for T will specify a function A:[ν]to {-1, 0, 1} along with a partition (P) of [ν] such that the following rules apply to the tensors and morphisms in the category.

(1)
for each tensor T framed by [Uν, ..., U0], if X∈(P), then forall i, j∈X, Ui=Uj.

(2)
Given a second tensor S framed by [Vv, ..., V0], a morphism f:T to S (Magma type Hmtp) will be a list [fν, ..., f0] of homomorphisms as follows:
(Covariant) if A(i)=1 then fi:Uito Vi;
(Constant) if A(i)=0 then Ui=Vi and fi=1Ui; or else
(Contravariant) A(i)= - 1 and fi:Ui <- Vi. So if A(0)=1 then < ∑_(i∈A - 1(1)) ui fi + ∑_(j not∈A - 1( - 1)) vj >S = < ∑_(i∈A - 1(1)) ui + ∑_(j not∈A - 1( - 1)) vj fj >T f0; if A(0)=0 then < ∑_(i∈A - 1(1)) ui fi + ∑_(j not∈A - 1( - 1)) vj >S = < ∑_(i∈A - 1(1)) ui + ∑_(j not∈A - 1( - 1)) vj fj >T; else A(0)= - 1 and < ∑_(i∈A - 1(1)) ui fi + ∑_(j not∈A - 1( - 1)) vj >S f0 = < ∑_(i∈A - 1(1)) ui + ∑_(j not∈A - 1( - 1)) vj fj >T.

Magma manages internally the differences between vectors and covectors and more generally tensors and cotensors. Both types are issued the Magma type TenSpcElt. For operations sensitive to the difference, Magma stores a value of co/contra-variance of the tensor as a property of the tensor category. This is the third general property stored in Magma's tensor category type TenCat.

We use the phrase tensor category exclusively for categories that describe tensors and tensor spaces. In other words, the data structure of a tensor category is a function A:[ν] -> {-1, 0, 1} and a partition (P) of [ν]. It is useful to distinguish from tensors and cotensors at the categorical level, so a tensor category is either covariant or contravariant as well (in the latter case, referred to as a cotensor category).

Contents

Constructing Tensor Categories

TensorCategory(A, P) : [RngIntElt], SetEnum -> TenCat
TensorCategory(A, P) : Map, SetEnum -> TenCat
Sets up a covariant tensor space category with specified direction of arrows A, and a partition (P) indicating variables to be treated as equivalent. The fiber A - 1(1) denotes the covariant variables, A - 1(0) identifies the constant variables, and A - 1( - 1) marks the contra-variant variables.
CotensorCategory(A, P) : [RngIntElt], SetEnum -> TenCat
CotensorCategory(A, P) : Map, SetEnum -> TenCat
Sets up a contra-variant tensor space category with specified direction of arrows A, and a partition (P) indicating variables to be treated as equivalent. The fiber A - 1(1) denotes the covariant variables, A - 1(0) identifies the constant variables, and A - 1( - 1) marks the contra-variant variables.

Example Multilinear_BasicCatConst (H62E61)

We demonstrate the basic tensor category constructor. The difference between TensorCategory and CotensorCategory is only that the former is covariant and the latter is contravariant.

> C := TensorCategory([1,0,-1], {{0},{1},{2}});
> C;
Tensor category of valence 3 (->,==,<-) ({ 1 },{ 2 },{ 0 })
> IsCovariant(C);
true
>
> arrows := map< {1..5} -> {1} | x :-> 1 >;
> C := CotensorCategory(arrows, {{1..5}});
> C;
Cotensor category of valence 6 (->,->,->,->,->,==) ({ 0 },{ 1 .. 5 })
> IsContravariant(C);
true
HomotopismCategory(v : parameters) : RngIntElt -> TenCat
    Contravariant: BoolElt              Default: false
Returns Albert's homotopism category -- all modules categories are covariant and no duplicates considered. Set the optional parameter Contravariant to true to make it a cotensor category.
CohomotopismCategory(v) : RngIntElt -> TenCat
Returns the cohomotopism category -- all domain modules categories are covariant, the codomain is contravariant, and no duplicates considered.
AdjointCategory(v, s, t) : RngIntElt, RngIntElt, RngIntElt -> TenCat
LinearCategory(v, s, t) : RngIntElt, RngIntElt, RngIntElt -> TenCat
Returns the tensor category where all modules are constant except in position s and t. Both s and t are in [v]. Position s is covariant, position t is contravariant.

Example Multilinear_TenCatSpecial (H62E62)

Now we look at a few special tensor category constructors. The default tensor category is the homotopism category, so we construct the homotopism category using TensorCategory and verify they are equivalent.

> C := TensorCategory([1,1,1,1], {{i} : i in [0..3]});
> C;
Tensor category of valence 4 (->,->,->,->) ({ 1 },{ 2 },{ 0 },{ 3 })
> HomotopismCategory(4) eq C;
true

The other special tensor categories can be constructed using TensorCategory as well, but we just construct a few to show their properties.

> CohomotopismCategory(3);
Tensor category of valence 3 (->,->,<-) ({ 1 },{ 2 },{ 0 })
>
> AdjointCategory(5, 4, 1);
Tensor category of valence 5 (<-,==,==,->,==) ({ 1 },{ 0, 2, 3 },{ 4 })

Operations on Tensor Categories

In this section the basic operations for tensor categories are described.

C1 eq C2 : TenCat, TenCat -> BoolElt
Returns true if the tensor categories are the same.
Valence(C) : TenCat -> RngIntElt
Returns the valence of the tensor category.
Arrows(C) : TenCat -> SeqEnum
Returns the sequence of arrows of the tensor category. A -1 signifies a contravariant index, a 0 signifies a constant index, and a 1 signifies a covariant index.
RepeatPartition(C) : TenCat -> SetEnum
Returns the repeat partition for the tensor category.
IsCovariant(C) : TenCat -> BoolElt
IsContravariant(C) : TenCat -> BoolElt
Returns true if the tensor category is covariant or contravariant.

Example Multilinear_TenCatProperties (H62E63)

We obtain basic properties of tensor categories.

> C := CotensorCategory([1,0,-1,1],{{4,3},{1},{2}});
> C;
Cotensor category of valence 5 (->,==,<-,->,==) ({ 1 },{ 2 },{ 0 },{ 3, 4 })
>
> Valence(C);
5
> Arrows(C);
[ 1, 0, -1, 1 ]
> IsContravariant(C);
true
> RepeatPartition(C);
{
    { 1 },
    { 2 },
    { 3, 4 }
}

Categorical Operations

In this section, we define subtensors, local ideals, ideals, and quotients of tensors. For the following definitions fix a tensor t∈T, with frame oslasha∈[ν]Ua---that is Uν x ... x U1 ↣ U0.

A tensor s:Vν x ... x V1 ↣ V0 is a subtensor of t if for all a, Va≤Ua.

For A⊆[ν] - 0, a tensor s:Vν x ... x V1 ↣ V0 is an A-local ideal of t if s is a subtensor of t and for each a∈A, < s | Vν, ..., Va + 1, Ua, Va - 1, ..., V1 > ≤V0.

A tensor s is an ideal of t if it is a {1, ..., ν}-local ideal of t.

The A-local quotient of a tensor t by an A-local ideal s is the tensor q:Uν/Vν x ... x U1/V1 ↣ U0/V0 where for all | /line(ν) >, < q | /line(ν) > ≡ < q | ν > (mod) V0.

The quotient of a tensor t by an ideal s is the {1, ..., ν}-local quotient of t by s.

Categorical Operations on Tensors

We include functions defined for the category of tensors. Most functions are currently defined only for the homotopism category.

Subtensor(T, S) : TenSpcElt, List -> TenSpcElt
Subtensor(T, S) : TenSpcElt, SeqEnum -> TenSpcElt
Returns the smallest submap of T containing S.
Subtensor(T, D, C) : TenSpcElt, List, Any -> TenSpcElt
Subtensor(T, D, C) : TenSpcElt, SeqEnum, Any -> TenSpcElt
Returns the smallest submap of T containing D in the domain and C in the codomain.
IsSubtensor(T, S) : TenSpcElt, TenSpcElt -> BoolElt
Decides whether S is a subtensor of T.

Example Multilinear_Subtensors (H62E64)

We construct the tensor t given by octonion multiplication. The quaternions H are a subalgebra of A= O generated by the first four basis elements. However, H cannot be coerced into A because of how Magma organizes algebras.

> A := OctonionAlgebra(Rationals(), -1, -1, -1);
> t := Tensor(A);
> t;
Tensor of valence 3, U2 x U1 >-> U0
U2 : Full Vector space of degree 8 over Rational Field
U1 : Full Vector space of degree 8 over Rational Field
U0 : Full Vector space of degree 8 over Rational Field
> H := sub< A | A.1, A.2, A.3, A.4 >;
> H;
Algebra of dimension 4 with base ring Rational Field

There are multiple ways to get the subtensor of multiplication from H. We will create H x H ↣ H as a subtensor of A x A ↣ A.

> H_gens := [A.i : i in [1..4]];
> s := Subtensor(t, [*H_gens, H_gens, A!0*]);
> s;
Tensor of valence 3, U2 x U1 >-> U0
U2 : Vector space of degree 8, dimension 4 over Rational Field
Generators:
(1 0 0 0 0 0 0 0)
(0 1 0 0 0 0 0 0)
(0 0 1 0 0 0 0 0)
(0 0 0 1 0 0 0 0)
Echelonized basis:
(1 0 0 0 0 0 0 0)
(0 1 0 0 0 0 0 0)
(0 0 1 0 0 0 0 0)
(0 0 0 1 0 0 0 0)
U1 : Vector space of degree 8, dimension 4 over Rational Field
Generators:
(1 0 0 0 0 0 0 0)
(0 1 0 0 0 0 0 0)
(0 0 1 0 0 0 0 0)
(0 0 0 1 0 0 0 0)
Echelonized basis:
(1 0 0 0 0 0 0 0)
(0 1 0 0 0 0 0 0)
(0 0 1 0 0 0 0 0)
(0 0 0 1 0 0 0 0)
U0 : Vector space of degree 8, dimension 4 over Rational Field
Generators:
(1 0 0 0 0 0 0 0)
(0 1 0 0 0 0 0 0)
(0 0 1 0 0 0 0 0)
(0 0 0 1 0 0 0 0)
Echelonized basis:
(1 0 0 0 0 0 0 0)
(0 1 0 0 0 0 0 0)
(0 0 1 0 0 0 0 0)
(0 0 0 1 0 0 0 0)
Note that because H cannot be coerced into A (i.e. A!H produces an error), a subtensor of AlgGen cannot be done by Subtensor(t, [H, H, H]). Now we will construct the tensor straight from H. There is a subtle difference between the subtensor from A and the tensor from H---namely, the frame is different.
> s2 := Tensor(H);
> s2;
Tensor of valence 3, U2 x U1 >-> U0
U2 : Full Vector space of degree 4 over Rational Field
U1 : Full Vector space of degree 4 over Rational Field
U0 : Full Vector space of degree 4 over Rational Field
> s eq s2;
false
> Eltseq(s) eq Eltseq(s2);
true
LocalIdeal(T, S, I) : TenSpcElt, List, RngIntElt -> TenSpcElt
LocalIdeal(T, S, I) : TenSpcElt, SeqEnum, RngIntElt -> TenSpcElt
Returns the local ideal of T at I containing S.
LocalIdeal(T, D, C, I) : TenSpcElt, List, Any, RngIntElt -> TenSpcElt
LocalIdeal(T, D, C, I) : TenSpcElt, SeqEnum, Any, RngIntElt -> TenSpcElt
Returns the local ideal of T at I containing D in the domain and C in the codomain.
LocalIdeal(T, S, I) : TenSpcElt, TenSpcElt, RngIntElt -> TenSpcElt
Returns the local ideal of T at I containing S as a submap.
IsLocalIdeal(T, S, I) : TenSpcElt, TenSpcElt, RngIntElt -> BoolElt
Decides if S is a local ideal of T at I.

Example Multilinear_LocalIdeals (H62E65)

We use the same tensor t as the previous example, multiplication in A= O , and we construct the subtensor t2 given by multiplication in H. We construct a subtensor s of t as the submap containing < A2 > x < A1, A4 > ↣ < 0 >, which is equal to < A2 > x < A1, A4 > ↣ < A2A1, A2A4 >.

> A := OctonionAlgebra(Rationals(), -1, -1, -1);
> t := Tensor(A);
> t;
Tensor of valence 3, U2 x U1 >-> U0
U2 : Full Vector space of degree 8 over Rational Field
U1 : Full Vector space of degree 8 over Rational Field
U0 : Full Vector space of degree 8 over Rational Field
> H_gens := [A.i : i in [1..4]];
> t2 := Subtensor(t, [*H_gens, H_gens, H_gens*]);
> s := Subtensor(t, [* A.2, [A.1, A.4], A!0 *]);
> s;
Tensor of valence 3, U2 x U1 >-> U0
U2 : Vector space of degree 8, dimension 1 over Rational Field
Generators:
(0 1 0 0 0 0 0 0)
Echelonized basis:
(0 1 0 0 0 0 0 0)
U1 : Vector space of degree 8, dimension 2 over Rational Field
Generators:
(1 0 0 0 0 0 0 0)
(0 0 0 1 0 0 0 0)
Echelonized basis:
(1 0 0 0 0 0 0 0)
(0 0 0 1 0 0 0 0)
U0 : Vector space of degree 8, dimension 2 over Rational Field
Generators:
(0 1 0 0 0 0 0 0)
(0 0 1 0 0 0 0 0)
Echelonized basis:
(0 1 0 0 0 0 0 0)
(0 0 1 0 0 0 0 0)

The quaternions are a subalgebra of A generated by {A1, A2, A3, A4}. Therefore, the {2}-local ideal of s in t must contain A in the codomain. However, the {2}-local ideal of s in t2 must only contain < A1, A2, A3, A4} in the codomain.

> s1 := LocalIdeal(t, s, {2});
> Codomain(s1);
Full Vector space of degree 8 over Rational Field
Generators:
(1 0 0 0 0 0 0 0)
(0 1 0 0 0 0 0 0)
(0 0 1 0 0 0 0 0)
(0 0 0 1 0 0 0 0)
(0 0 0 0 1 0 0 0)
(0 0 0 0 0 1 0 0)
(0 0 0 0 0 0 1 0)
(0 0 0 0 0 0 0 1)
> s2 := LocalIdeal(t2, s, {2});
> Codomain(s2);
Vector space of degree 8, dimension 4 over Rational Field
Generators:
(1 0 0 0 0 0 0 0)
(0 1 0 0 0 0 0 0)
(0 0 1 0 0 0 0 0)
(0 0 0 1 0 0 0 0)
Echelonized basis:
(1 0 0 0 0 0 0 0)
(0 1 0 0 0 0 0 0)
(0 0 1 0 0 0 0 0)
(0 0 0 1 0 0 0 0)
Ideal(T, S) : TenSpcElt, List -> TenSpcElt
Ideal(T, S) : TenSpcElt, SeqEnum -> TenSpcElt
Returns the ideal of T containing S.
Ideal(T, D, C) : TenSpcElt, List, Any -> TenSpcElt
Ideal(T, D, C) : TenSpcElt, SeqEnum, Any -> TenSpcElt
Returns the ideal of T containing D in the domain and C in the codomain.
Ideal(T, S) : TenSpcElt, TenSpcElt -> TenSpcElt
Returns the ideal of T containing S as a submap.
IsIdeal(T, S) : TenSpcElt, TenSpcElt -> BoolElt
Decides if S is an ideal of T.

Example Multilinear_Ideals (H62E66)

First we will construct the tensor from the Q-algebra, Q5.

> T := KTensorSpace(Rationals(), [5,5,5]);
> A := VectorSpace(Rationals(), 5);
> t := T!0;
> for i in [1..5] do
>   Assign(~t, [i,i,i], 1);
> end for;
> t;
Tensor of valence 3, U2 x U1 >-> U0
U2 : Full Vector space of degree 5 over Rational Field
U1 : Full Vector space of degree 5 over Rational Field
U0 : Full Vector space of degree 5 over Rational Field
> SystemOfForms(t);
[
    [1 0 0 0 0]
    [0 0 0 0 0]
    [0 0 0 0 0]
    [0 0 0 0 0]
    [0 0 0 0 0],
    [0 0 0 0 0]
    [0 1 0 0 0]
    [0 0 0 0 0]
    [0 0 0 0 0]
    [0 0 0 0 0],
    [0 0 0 0 0]
    [0 0 0 0 0]
    [0 0 1 0 0]
    [0 0 0 0 0]
    [0 0 0 0 0],
    [0 0 0 0 0]
    [0 0 0 0 0]
    [0 0 0 0 0]
    [0 0 0 1 0]
    [0 0 0 0 0],
    [0 0 0 0 0]
    [0 0 0 0 0]
    [0 0 0 0 0]
    [0 0 0 0 0]
    [0 0 0 0 1]
]

Now we will construct the ideal tensor from the subtensor containing < A1 > x < A2 > ↣ < A3 >. Note that the {2}-local ideal must include < A2, A3 > in the codomain, and the {1}-local ideal must contain < A1, A3 > in the codomain.

> s := Ideal(t, [A.1, A.2, A.3]);
> s;
Tensor of valence 3, U2 x U1 >-> U0
U2 : Vector space of degree 5, dimension 1 over Rational Field
Generators:
(1 0 0 0 0)
Echelonized basis:
(1 0 0 0 0)
U1 : Vector space of degree 5, dimension 1 over Rational Field
Generators:
(0 1 0 0 0)
Echelonized basis:
(0 1 0 0 0)
U0 : Vector space of degree 5, dimension 3 over Rational Field
Generators:
(1 0 0 0 0)
(0 1 0 0 0)
(0 0 1 0 0)
Echelonized basis:
(1 0 0 0 0)
(0 1 0 0 0)
(0 0 1 0 0)

Finally, we verify that the subtensor containing < A1 > x < A2 > ↣ < A2, A3 > is not an ideal.

> r := Subtensor(t, [A.1, A.2], [A.2, A.3]);
> IsIdeal(t, r);
false
LocalQuotient(T, S, I : parameters) : TenSpcElt, TenSpcElt, RngIntElt -> TenSpcElt, Hmtp
    Check: BoolElt                      Default: true
Returns the local quotient of T by S at I⊆[ν] - 0. If you know S is a local ideal of T at I, set Check to false to skip the verification. A homotopism is also returned, mapping from T to T/S.
Quotient(T, S : parameters) : TenSpcElt, TenSpcElt -> TenSpcElt, Hmtp
    Check: BoolElt                      Default: true
T / S : TenSpcElt, TenSpcElt -> TenSpcElt, Hmtp
Returns the quotient of T by S. If you know S is an ideal of T, set Check to false to skip the verification. A homotopism is also returned, mapping from T to T/S.

Example Multilinear_Quotients (H62E67)

We will demonstrate one of the most common uses for quotienting tensors: constructing the associated fully nondegenerate tensor. We first construct a tensor with a nontrivial radical given by matrix multiplication: (Mat)3 x 2(Q) x Q3 ↣ Q3, where we take a projection of Q3 onto Q2 in the 1 coordinate.

> K := Rationals();
> F := [*KMatrixSpace(K, 3, 2), VectorSpace(K, 3), VectorSpace(K, 3)*];
> mult := function(x)
>   return Transpose(x[1]*Matrix(2, 1, Eltseq(x[2])[2..3]));
> end function;
> t := Tensor(F, mult);
> t;
Tensor of valence 3, U2 x U1 >-> U0
U2 : Full Vector space of degree 6 over Rational Field
U1 : Full Vector space of degree 3 over Rational Field
U0 : Full Vector space of degree 3 over Rational Field
> s := Subtensor(t, [*[F[1].1, F[1].4], F[2], F[3]*]);
> s;
Tensor of valence 3, U2 x U1 >-> U0
U2 : Vector space of degree 6, dimension 2 over Rational Field
Generators:
(1 0 0 0 0 0)
(0 0 0 1 0 0)
Echelonized basis:
(1 0 0 0 0 0)
(0 0 0 1 0 0)
U1 : Full Vector space of degree 3 over Rational Field
Generators:
(1 0 0)
(0 1 0)
(0 0 1)
U0 : Full Vector space of degree 3 over Rational Field
Generators:
(1 0 0)
(0 1 0)
(0 0 1)
> IsFullyNondegenerate(s);
false

Now we will construct the ideal r that evaluates to 0 and the largest subspace of Q3 not contained in the image.

> r := Ideal(t, [*F[1]!0, F[2].1, F[3].3*]);
> r;
Tensor of valence 3, U2 x U1 >-> U0
U2 : Vector space of degree 6, dimension 0 over Rational Field
Generators:
U1 : Vector space of degree 3, dimension 1 over Rational Field
Generators:
(1 0 0)
Echelonized basis:
(1 0 0)
U0 : Vector space of degree 3, dimension 1 over Rational Field
Generators:
(0 0 1)
Echelonized basis:
(0 0 1)
> IsIdeal(t, r);
true

Finally, we quotient s by r to obtain a fully nondegenerate tensor.

> q := s/r;
> q;
Tensor of valence 3, U2 x U1 >-> U0
U2 : Full Vector space of degree 2 over Rational Field
U1 : Full Vector space of degree 2 over Rational Field
U0 : Full Vector space of degree 2 over Rational Field
> IsFullyNondegenerate(q);
true
Categorical Operations on Tensor Spaces

We have categorical notions for tensor spaces as well, and these are inherited from the module structure on tensor spaces.

SubConstructor(T, L) : TenSpc, Any -> TenSpc, Map
sub< T | L > : TenSpc, Any -> TenSpc, Map
Returns the subtensor space of T generated by the tensors in the sequence L.
IsSubtensorSpace(T, S) : TenSpc, TenSpc -> BoolElt
Decides if the tensor space S is a subtensor space of T.

Example Multilinear_SubtensorSpaces (H62E68)

We will construct the subspace S of symmetric forms from the tensor space T with frame Q2 x Q2 ↣ Q.

> K := Rationals();
> T := KTensorSpace(K, [2,2,1]);
> T;
Tensor space of dimension 4 over Rational Field with valence 3
U2 : Full Vector space of degree 2 over Rational Field
U1 : Full Vector space of degree 2 over Rational Field
U0 : Full Vector space of degree 1 over Rational Field
> S := sub< T | T.1, T.2+T.3, T.4 >;
> S;
Tensor space of dimension 3 over Rational Field with valence 3
U2 : Full Vector space of degree 2 over Rational Field
U1 : Full Vector space of degree 2 over Rational Field
U0 : Full Vector space of degree 1 over Rational Field
> IsSymmetric(S);
true

Now we will construct the subspace A of alternating forms from T.

> A := sub< T | T.2-T.3 >;
> A;
Tensor space of dimension 1 over Rational Field with valence 3
U2 : Full Vector space of degree 2 over Rational Field
U1 : Full Vector space of degree 2 over Rational Field
U0 : Full Vector space of degree 1 over Rational Field
> IsAlternating(A);
true

Now we verify that A is not a subtensor space of S, and thus, we have constructed a direct decomposition of T into its symmetric and alternating space.

> IsSubtensorSpace(S, A);
false
QuoConstructor(T, X) : TenSpc, Any -> TenSpc, Map
quo< T | X > : TenSpc, Any -> TenSpc, Map
T / S : TenSpc, TenSpc -> TenSpc, Map
Returns the quotient tensor space of T by S.

Example Multilinear_QuotientTensorSpaces (H62E69)

We pick up with the same tensor spaces as the previous example: T has frame Q2 x Q2 ↣ Q, S is the symmetric subspace, and A is the alternating subspace.

> K := Rationals();
> T := KTensorSpace(K, [2,2,1]);
> T;
Tensor space of dimension 4 over Rational Field with valence 3
U2 : Full Vector space of degree 2 over Rational Field
U1 : Full Vector space of degree 2 over Rational Field
U0 : Full Vector space of degree 1 over Rational Field
> S := sub< T | T.1, T.2+T.3, T.4 >;
> A := sub< T | T.2-T.3 >;

Now we construct the quotient of T by A. The result is not a symmetric tensor space. Note that Q2 is equivalent to a symmetric tensor modulo A, but this choice is arbitrary.

> Q := T/A;
> Q;
Tensor space of dimension 3 over Rational Field with valence 3
U2 : Full Vector space of degree 2 over Rational Field
U1 : Full Vector space of degree 2 over Rational Field
U0 : Full Vector space of degree 1 over Rational Field
> SystemOfForms(Q.1);
[
    [1 0]
    [0 0]
]
> SystemOfForms(Q.2);
[
    [0 0]
    [1 0]
]
> SystemOfForms(Q.3);
[
    [0 0]
    [0 1]
]

Homotopisms

Magma provides functions for homotopisms, i.e. morphisms of tensors. Homotopisms are also equipped with a tensor category. Because homotopisms can contain multiple maps between modules, it is not really clear what is meant by the domain or codomain of a given homotopism. In this context, the domain of a homotopism H will refer to the tensor, t:Uν x ... x U1 ↣ U0, where an arrow equal to 1 at coordinate a will mean that the corresponding map at coordinate a has domain equal to Ua. And in the same vain, the tensor s:Vν x ... x V1 ↣ V0 is the codomain of H if an arrow equal to 1 at coordinate a implies that the corresponding map at coordinate a has codomain equal to Va.

Constructions of Homotopisms
Homotopism(T, S, M : parameters) : TenSpcElt, TenSpcElt, List -> Hmtp
Homotopism(T, S, M : parameters) : TenSpcElt, TenSpcElt, SeqEnum -> Hmtp
    Check: BoolElt                      Default: true
Homotopism(T, S, M, C : parameters) : TenSpcElt, TenSpcElt, List, TenCat -> Hmtp
Homotopism(T, S, M, C : parameters) : TenSpcElt, TenSpcElt, SeqEnum, TenCat -> Hmtp
    Check: BoolElt                      Default: true
Returns the homotopism from T to S given by the list of maps M and the category C. The default tensor category is the same as tensor categories for T and S. If the maps M will produce a homotopism, then set Check to false to skip the verification.
Homotopism(M, C) : List, TenCat -> Hmtp
Homotopism(M, C) : SeqEnum, TenCat -> Hmtp
Returns the homotopism given by the maps in M with tensor category C.
IsHomotopism(T, s, H) : TenSpcElt, TenSpcElt, Hmtp -> BoolElt
IsHomotopism(T, s, M) : TenSpcElt, TenSpcElt, List -> BoolElt
IsHomotopism(T, s, M) : TenSpcElt, TenSpcElt, SeqEnum -> BoolElt
IsHomotopism(T, s, M, C) : TenSpcElt, TenSpcElt, List, TenCat -> BoolElt
IsHomotopism(T, s, M, C) : TenSpcElt, TenSpcElt, SeqEnum, TenCat -> BoolElt
Decides if the list of maps M induces a homotopism from T to S in the tensor category C. The default tensor category is the homotopism category. If it does induce a homotopism, it is also returned.

Example Multilinear_HomotopismConst (H62E70)

We will construct two symmetric tensors t, s: GF(3)3 x GF(3)3 ↣ GF(3)3 and apply permutations to the bases.

> T := KTensorSpace(GF(3), [3,3,3]);
> t := T.1+T.14+T.27;
> SystemOfForms(t);
[
    [1 0 0]
    [0 0 0]
    [0 0 0],
    [0 0 0]
    [0 1 0]
    [0 0 0],
    [0 0 0]
    [0 0 0]
    [0 0 1]
]
> s := (T.4+T.10)+(T.8+T.20)+(T.18+T.24);
> SystemOfForms(s);
[
    [0 1 0]
    [1 0 0]
    [0 0 0],
    [0 0 1]
    [0 0 0]
    [1 0 0],
    [0 0 0]
    [0 0 1]
    [0 1 0]
]

Now we construct a homotopism from t to t given by apply a permutation matrix in every coordinate.

> P := PermutationMatrix(GF(3), [2,1,3]);
> H := Homotopism(t, t, [*P, P, P*]);
> H;
Maps from U2 x U1 >-> U0 to V2 x V1 >-> V0.
U2 -> V2:
[0 1 0]
[1 0 0]
[0 0 1]
U1 -> V1:
[0 1 0]
[1 0 0]
[0 0 1]
U0 -> V0:
[0 1 0]
[1 0 0]
[0 0 1]

Note that this permutation matrix does not induce a homotopism of s.

> IsHomotopism(s, s, [*P, P, P*]);
false

Example Multilinear_MixedHomotopisms (H62E71)

Homotopisms can take mixed categories of maps. To reuse the above example, we can encode the permutation as a Map and construct homotopisms from these types.
> V := VectorSpace(GF(3), 3);
> T := TensorSpace([V, V, V]);
> t := T.1+T.14+T.27;
> P := PermutationMatrix(GF(3), [2,1,3]);
> f := hom< V -> V | [<V.1, V.2>, <V.2, V.1>, <V.3, V.3>] >;
> H := Homotopism(t, t, [*f, f, f*]);
> H;
Maps from U2 x U1 >-> U0 to V2 x V1 >-> V0.
U2 -> V2: Mapping from: Full Vector space of degree 3 over GF(3) to Full
Vector space of degree 3 over GF(3)
U1 -> V1: Mapping from: Full Vector space of degree 3 over GF(3) to Full
Vector space of degree 3 over GF(3)
U0 -> V0: Mapping from: Full Vector space of degree 3 over GF(3) to Full
Vector space of degree 3 over GF(3)

Furthermore, we can input lists with types Mtrx and Map included.

> H2 := Homotopism(t, t, [*P, f, P*]);
> H2;
Maps from U2 x U1 >-> U0 to V2 x V1 >-> V0.
U2 -> V2:
[0 1 0]
[1 0 0]
[0 0 1]
U1 -> V1: Mapping from: Full Vector space of degree 3 over GF(3) to Full
Vector space of degree 3 over GF(3)
U0 -> V0:
[0 1 0]
[1 0 0]
[0 0 1]
Basic Operations with Homotopisms

We provide some operations for homotopisms.

H1 * H2 : Hmtp, Hmtp -> Hmtp
Returns the composition of the homotopisms H1 and H2.
H . a : Hmtp, RngIntElt -> Map
Returns the map on the ath coordinate.

Example Multilinear_HomotopismOps (H62E72)

We construct a nondegenerate alternating form t on V=Q6. The group of isometries are isomorphic to (Sp)(6, Q), the group generated by all transvections. We construct a transvection L and a corresponding matrix.

> V := VectorSpace(Rationals(), 6);
> T := KTensorSpace(Rationals(), [6, 6, 1]);
> t := T.2-T.7+T.16-T.21+T.30-T.35;
> t;
Tensor of valence 3, U2 x U1 >-> U0
U2 : Full Vector space of degree 6 over Rational Field
U1 : Full Vector space of degree 6 over Rational Field
U0 : Full Vector space of degree 1 over Rational Field
>
> u := V.2+2*V.3-V.5;
> L := map< V -> V | x :-> x + (x*t*u)[1]*u >;
> L;
Mapping from: ModTupFld: V to ModTupFld: V given by a rule [no inverse]
> M := Matrix(6, 6, [V.i @ L : i in [1..6]]);
> M;
[ 1  1  2  0 -1  0]
[ 0  1  0  0  0  0]
[ 0  0  1  0  0  0]
[ 0 -2 -4  1  2  0]
[ 0  0  0  0  1  0]
[ 0  1  2  0 -1  1]

We construct a homotopism from the transvection.

> H := Homotopism(t, t, [*L, L, IdentityMatrix(Rationals(), 1)*]);
> H;
Maps from U2 x U1 >-> U0 to V2 x V1 >-> V0.
U2 -> V2: Mapping from: Full Vector space of degree 6 over Rational Field to
Full Vector space of degree 6 over Rational Field given by a rule [no inverse]
U1 -> V1: Mapping from: Full Vector space of degree 6 over Rational Field to
Full Vector space of degree 6 over Rational Field given by a rule [no inverse]
U0 -> V0:
[1]

Since H is an isometry of t, H2 is also an isometry of t. We verify that the 2-coordinate map of H2 is exactly M2.

> H2 := H*H;
> H2;
Maps from U2 x U1 >-> U0 to V2 x V1 >-> V0.
U2 -> V2: Mapping from: Full Vector space of degree 6 over Rational Field to
Full Vector space of degree 6 over Rational Field
Composition of Mapping from: Full Vector space of degree 6 over Rational Field
to Full Vector space of degree 6 over Rational Field given by a rule [no
inverse] and
Mapping from: Full Vector space of degree 6 over Rational Field to Full Vector
space of degree 6 over Rational Field given by a rule [no inverse]
U1 -> V1: Mapping from: Full Vector space of degree 6 over Rational Field to
Full Vector space of degree 6 over Rational Field
Composition of Mapping from: Full Vector space of degree 6 over Rational Field
to Full Vector space of degree 6 over Rational Field given by a rule [no
inverse] and
Mapping from: Full Vector space of degree 6 over Rational Field to Full Vector
space of degree 6 over Rational Field given by a rule [no inverse]
U0 -> V0:
[1]
> M2 := Matrix(6, 6, [V.i @ H2.2 : i in [1..6]]);
> M2;
[ 1  2  4  0 -2  0]
[ 0  1  0  0  0  0]
[ 0  0  1  0  0  0]
[ 0 -4 -8  1  4  0]
[ 0  0  0  0  1  0]
[ 0  2  4  0 -2  1]
> M^2 eq M2;
true
Precompose(T, f, a) : TenSpcElt, Map, RngIntElt -> TenSpcElt
Precompose(T, M, a) : TenSpcElt, Mtrx, RngIntElt -> TenSpcElt
If a>0, then the tensor returned is the tensor that has been pre-composed by the map f or matrix M.
T @ H : TenSpcElt, Hmtp -> TenSpcElt
If H is a cohomotopism (a homotopism in the cohomotopism category), then either the domain or codomain of H is returned, depending on the orientation of the arrows of H.
Basic Properties of Homotopisms
Domain(H) : Hmtp -> TenSpcElt
Returns the domain tensor of H.
Codomain(H) : Hmtp -> TenSpcElt
Returns the codomain tensor of H.
Maps(H) : Hmtp -> List
Returns the list of maps for the various modules in the domain and codomain tensors.
TensorCategory(H) : Hmtp -> TenCat
Returns the tensor category of H.
ChangeTensorCategory(H, C) : Hmtp, TenCat -> Hmtp
ChangeTensorCategory(~H, C) : Hmtp, TenCat ->
Changes the tensor category of H to the given category.
Valence(H) : Hmtp -> RngIntElt
Returns the valence of the underlying tensor category of the homotopism H.
Kernel(H) : Hmtp -> TenSpcElt
Returns the kernel of H as an ideal of its domain tensor.
Image(H) : Hmtp -> TenSpcElt
Returns the image of H as a submap of the codomain tensor.

Example Multilinear_HomotopismProps (H62E73)

We demonstrate how to access properties of a homotopism. We construct tensors t:Q4 x Q4 ↣ Q and s:Q6 x Q6 ↣ Q given by the dot product.

> t := Tensor(IdentityMatrix(Rationals(), 4), 2, 1);
> s := Tensor(IdentityMatrix(Rationals(), 6), 2, 1);
> Z := ZeroMatrix(Rationals(), 4, 6);
> M := InsertBlock(Z, IdentityMatrix(Rationals(), 4), 1, 1);
> H := Homotopism(t, s, [*M, M, IdentityMatrix(Rationals(), 1)*]);
> H;
Maps from U2 x U1 >-> U0 to V2 x V1 >-> V0.
U2 -> V2:
[1 0 0 0 0 0]
[0 1 0 0 0 0]
[0 0 1 0 0 0]
[0 0 0 1 0 0]
U1 -> V1:
[1 0 0 0 0 0]
[0 1 0 0 0 0]
[0 0 1 0 0 0]
[0 0 0 1 0 0]
U0 -> V0:
[1]

Like with maps, we can obtain standard properties of homotopisms.

> Domain(H);
Tensor of valence 3, U2 x U1 >-> U0
U2 : Full Vector space of degree 4 over Rational Field
U1 : Full Vector space of degree 4 over Rational Field
U0 : Full Vector space of degree 1 over Rational Field
> Codomain(H);
Tensor of valence 3, U2 x U1 >-> U0
U2 : Full Vector space of degree 6 over Rational Field
U1 : Full Vector space of degree 6 over Rational Field
U0 : Full Vector space of degree 1 over Rational Field
> Maps(H);
[*
    [1 0 0 0 0 0]
    [0 1 0 0 0 0]
    [0 0 1 0 0 0]
    [0 0 0 1 0 0],
    [1 0 0 0 0 0]
    [0 1 0 0 0 0]
    [0 0 1 0 0 0]
    [0 0 0 1 0 0],
    [1]
*]
> TensorCategory(H);
Tensor category of valence 3 (->,->,->) ({ 1 },{ 2 },{ 0 })

When the image and kernel can be computed for the each of the maps in the homotopism, then the image and kernel can be computed for the homotopism.

> Im := Image(H);
> Im;
Tensor of valence 3, U2 x U1 >-> U0
U2 : Vector space of degree 6, dimension 4 over Rational Field
Echelonized basis:
(1 0 0 0 0 0)
(0 1 0 0 0 0)
(0 0 1 0 0 0)
(0 0 0 1 0 0)
U1 : Vector space of degree 6, dimension 4 over Rational Field
Echelonized basis:
(1 0 0 0 0 0)
(0 1 0 0 0 0)
(0 0 1 0 0 0)
(0 0 0 1 0 0)
U0 : Full Vector space of degree 1 over Rational Field
> Ker := Kernel(H);
> Ker;
Tensor of valence 3, U2 x U1 >-> U0
U2 : Vector space of degree 4, dimension 0 over Rational Field
U1 : Vector space of degree 4, dimension 0 over Rational Field
U0 : Vector space of degree 1, dimension 0 over Rational Field
Shuffle(H, g) : Hmtp, GrpPermElt -> Hmtp
Shuffle(H, g) : Hmtp, [RngIntElt] -> Hmtp
Just like the shuffle for tensors, this returns the shuffle of the homotopism H. This is a functor from one tensor category to another and changes the order of the maps to {Hνg, ..., H1g, H0g}. In order to be defined, g∈Sym({0, ..., ν }). If 0g≠0, then both the image and pre-image of 0 under g will be replaced by their K-dual space. For cotensors, g∈Sym({1, ..., ν}). Sequences [a1, ..., aν + 1] will be interpreted as a permutation in one-line notation.
V2.28, 13 July 2023