From: Michael Orlitzky Date: Thu, 18 Jul 2019 22:54:43 +0000 (-0400) Subject: eja: maintain a "natural basis" for EJAs. X-Git-Url: https://gitweb.michael.orlitzky.com/?a=commitdiff_plain;h=8c905628c1d76cad7cc456e285688decd4205d0e;p=sage.d.git eja: maintain a "natural basis" for EJAs. This will eventually let us see the "usual" representation of an EJA element. In other words, we don't want to see (1,0,1) to indicate the identity element of the 2-by-2 symmetric matrices. --- diff --git a/mjo/eja/euclidean_jordan_algebra.py b/mjo/eja/euclidean_jordan_algebra.py index e2d644a..3124132 100644 --- a/mjo/eja/euclidean_jordan_algebra.py +++ b/mjo/eja/euclidean_jordan_algebra.py @@ -20,7 +20,8 @@ class FiniteDimensionalEuclideanJordanAlgebra(FiniteDimensionalAlgebra): names='e', assume_associative=False, category=None, - rank=None): + rank=None, + natural_basis=None): n = len(mult_table) mult_table = [b.base_extend(field) for b in mult_table] for b in mult_table: @@ -43,7 +44,8 @@ class FiniteDimensionalEuclideanJordanAlgebra(FiniteDimensionalAlgebra): assume_associative=assume_associative, names=names, category=cat, - rank=rank) + rank=rank, + natural_basis=natural_basis) def __init__(self, field, @@ -51,7 +53,8 @@ class FiniteDimensionalEuclideanJordanAlgebra(FiniteDimensionalAlgebra): names='e', assume_associative=False, category=None, - rank=None): + rank=None, + natural_basis=None): """ EXAMPLES: @@ -66,6 +69,7 @@ class FiniteDimensionalEuclideanJordanAlgebra(FiniteDimensionalAlgebra): """ self._rank = rank + self._natural_basis = natural_basis fda = super(FiniteDimensionalEuclideanJordanAlgebra, self) fda.__init__(field, mult_table, @@ -80,6 +84,49 @@ class FiniteDimensionalEuclideanJordanAlgebra(FiniteDimensionalAlgebra): fmt = "Euclidean Jordan algebra of degree {} over {}" return fmt.format(self.degree(), self.base_ring()) + + def natural_basis(self): + """ + Return a more-natural representation of this algebra's basis. + + Every finite-dimensional Euclidean Jordan Algebra is a direct + sum of five simple algebras, four of which comprise Hermitian + matrices. This method returns the original "natural" basis + for our underlying vector space. (Typically, the natural basis + is used to construct the multiplication table in the first place.) + + Note that this will always return a matrix. The standard basis + in `R^n` will be returned as `n`-by-`1` column matrices. + + EXAMPLES:: + + sage: J = RealSymmetricSimpleEJA(2) + sage: J.basis() + Family (e0, e1, e2) + sage: J.natural_basis() + ( + [1 0] [0 1] [0 0] + [0 0], [1 0], [0 1] + ) + + :: + + sage: J = JordanSpinSimpleEJA(2) + sage: J.basis() + Family (e0, e1) + sage: J.natural_basis() + ( + [1] [0] + [0], [1] + ) + + """ + if self._natural_basis is None: + return tuple( b.vector().column() for b in self.basis() ) + else: + return self._natural_basis + + def rank(self): """ Return the rank of this EJA. @@ -865,7 +912,7 @@ def _real_symmetric_basis(n, field=QQ): # Beware, orthogonal but not normalized! Sij = Eij + Eij.transpose() S.append(Sij) - return S + return tuple(S) def _complex_hermitian_basis(n, field=QQ): @@ -902,7 +949,7 @@ def _complex_hermitian_basis(n, field=QQ): S.append(Sij_real) Sij_imag = _embed_complex_matrix(I*Eij - I*Eij.transpose()) S.append(Sij_imag) - return S + return tuple(S) def _multiplication_table_from_matrix_basis(basis): @@ -912,7 +959,10 @@ def _multiplication_table_from_matrix_basis(basis): multiplication on the right is matrix multiplication. Given a basis for the underlying matrix space, this function returns a multiplication table (obtained by looping through the basis - elements) for an algebra of those matrices. + elements) for an algebra of those matrices. A reordered copy + of the basis is also returned to work around the fact that + the ``span()`` in this function will change the order of the basis + from what we think it is, to... something else. """ # In S^2, for example, we nominally have four coordinates even # though the space is of dimension three only. The vector space V @@ -934,7 +984,7 @@ def _multiplication_table_from_matrix_basis(basis): # Taking the span above reorders our basis (thanks, jerk!) so we # need to put our "matrix basis" in the same order as the # (reordered) vector basis. - S = [ vec2mat(b) for b in W.basis() ] + S = tuple( vec2mat(b) for b in W.basis() ) Qs = [] for s in S: @@ -952,7 +1002,7 @@ def _multiplication_table_from_matrix_basis(basis): Q = matrix(field, W.dimension(), Q_rows) Qs.append(Q) - return Qs + return (Qs, S) def _embed_complex_matrix(M): @@ -1059,9 +1109,12 @@ def RealSymmetricSimpleEJA(n, field=QQ): """ S = _real_symmetric_basis(n, field=field) - Qs = _multiplication_table_from_matrix_basis(S) + (Qs, T) = _multiplication_table_from_matrix_basis(S) - return FiniteDimensionalEuclideanJordanAlgebra(field,Qs,rank=n) + return FiniteDimensionalEuclideanJordanAlgebra(field, + Qs, + rank=n, + natural_basis=T) def ComplexHermitianSimpleEJA(n, field=QQ): @@ -1083,8 +1136,11 @@ def ComplexHermitianSimpleEJA(n, field=QQ): """ S = _complex_hermitian_basis(n) - Qs = _multiplication_table_from_matrix_basis(S) - return FiniteDimensionalEuclideanJordanAlgebra(field, Qs, rank=n) + (Qs, T) = _multiplication_table_from_matrix_basis(S) + return FiniteDimensionalEuclideanJordanAlgebra(field, + Qs, + rank=n, + natural_basis=T) def QuaternionHermitianSimpleEJA(n):