- def _a_regular_element(self):
- """
- Guess a regular element. Needed to compute the basis for our
- characteristic polynomial coefficients.
-
- SETUP::
-
- sage: from mjo.eja.eja_algebra import random_eja
-
- TESTS:
-
- Ensure that this hacky method succeeds for every algebra that we
- know how to construct::
-
- sage: set_random_seed()
- sage: J = random_eja()
- sage: J._a_regular_element().is_regular()
- True
-
- """
- gs = self.gens()
- z = self.sum( (i+1)*gs[i] for i in range(len(gs)) )
- if not z.is_regular():
- raise ValueError("don't know a regular element")
- return z
-
-
- @cached_method
- def _charpoly_basis_space(self):
- """
- Return the vector space spanned by the basis used in our
- characteristic polynomial coefficients. This is used not only to
- compute those coefficients, but also any time we need to
- evaluate the coefficients (like when we compute the trace or
- determinant).
- """
- z = self._a_regular_element()
- # Don't use the parent vector space directly here in case this
- # happens to be a subalgebra. In that case, we would be e.g.
- # two-dimensional but span_of_basis() would expect three
- # coordinates.
- V = VectorSpace(self.base_ring(), self.vector_space().dimension())
- basis = [ (z**k).to_vector() for k in range(self.rank()) ]
- V1 = V.span_of_basis( basis )
- b = (V1.basis() + V1.complement().basis())
- return V.span_of_basis(b)
-
-
-
- @cached_method
- def _charpoly_coeff(self, i):
- """
- Return the coefficient polynomial "a_{i}" of this algebra's
- general characteristic polynomial.
-
- Having this be a separate cached method lets us compute and
- store the trace/determinant (a_{r-1} and a_{0} respectively)
- separate from the entire characteristic polynomial.
- """
- (A_of_x, x, xr, detA) = self._charpoly_matrix_system()
- R = A_of_x.base_ring()
-
- if i == self.rank():
- return R.one()
- if i > self.rank():
- # Guaranteed by theory
- return R.zero()
-
- # Danger: the in-place modification is done for performance
- # reasons (reconstructing a matrix with huge polynomial
- # entries is slow), but I don't know how cached_method works,
- # so it's highly possible that we're modifying some global
- # list variable by reference, here. In other words, you
- # probably shouldn't call this method twice on the same
- # algebra, at the same time, in two threads
- Ai_orig = A_of_x.column(i)
- A_of_x.set_column(i,xr)
- numerator = A_of_x.det()
- A_of_x.set_column(i,Ai_orig)
-
- # We're relying on the theory here to ensure that each a_i is
- # indeed back in R, and the added negative signs are to make
- # the whole charpoly expression sum to zero.
- return R(-numerator/detA)
-
-