Path: blob/master/sage/modular/modform/eisenstein_submodule.py
4057 views
# -*- coding: utf-8 -*-1"""2The Eisenstein Subspace3"""45from sage.structure.all import Sequence6from sage.misc.all import verbose7import sage.rings.all as rings8from sage.categories.all import Objects9from sage.matrix.all import Matrix101112import eis_series13import element14import submodule1516class EisensteinSubmodule(submodule.ModularFormsSubmodule):17"""18The Eisenstein submodule of an ambient space of modular forms.19"""20def __init__(self, ambient_space):21"""22Return the Eisenstein submodule of the given space.2324EXAMPLES::2526sage: E = ModularForms(23,4).eisenstein_subspace() ## indirect doctest27sage: E28Eisenstein subspace of dimension 2 of Modular Forms space of dimension 7 for Congruence Subgroup Gamma0(23) of weight 4 over Rational Field29sage: E == loads(dumps(E))30True31"""32verbose('creating eisenstein submodule of %s'%ambient_space)33d = ambient_space._dim_eisenstein()34V = ambient_space.module()35n = V.dimension()36self._start_position = int(n - d)37S = V.submodule([V.gen(i) for i in range(n-d,n)], check=False,38already_echelonized=True)39submodule.ModularFormsSubmodule.__init__(self, ambient_space, S)4041def _repr_(self):42"""43Return the string representation of self.4445EXAMPLES::4647sage: E = ModularForms(23,4).eisenstein_subspace() ## indirect doctest48sage: E._repr_()49'Eisenstein subspace of dimension 2 of Modular Forms space of dimension 7 for Congruence Subgroup Gamma0(23) of weight 4 over Rational Field'50"""51return "Eisenstein subspace of dimension %s of %s"%(self.dimension(), self.ambient_module())5253def eisenstein_submodule(self):54"""55Return the Eisenstein submodule of self.56(Yes, this is just self.)5758EXAMPLES::5960sage: E = ModularForms(23,4).eisenstein_subspace()61sage: E == E.eisenstein_submodule()62True63"""64return self6566def modular_symbols(self, sign=0):67r"""68Return the corresponding space of modular symbols with given sign. This69will fail in weight 1.7071.. warning::7273If sign != 0, then the space of modular symbols will, in general,74only correspond to a *subspace* of this space of modular forms.75This can be the case for both sign +1 or -1.7677EXAMPLES::7879sage: E = ModularForms(11,2).eisenstein_submodule()80sage: M = E.modular_symbols(); M81Modular Symbols subspace of dimension 1 of Modular Symbols space82of dimension 3 for Gamma_0(11) of weight 2 with sign 0 over Rational Field83sage: M.sign()8408586sage: M = E.modular_symbols(sign=-1); M87Modular Symbols subspace of dimension 0 of Modular Symbols space of88dimension 1 for Gamma_0(11) of weight 2 with sign -1 over Rational Field8990sage: E = ModularForms(1,12).eisenstein_submodule()91sage: E.modular_symbols()92Modular Symbols subspace of dimension 1 of Modular Symbols space of93dimension 3 for Gamma_0(1) of weight 12 with sign 0 over Rational Field9495sage: eps = DirichletGroup(13).096sage: E = EisensteinForms(eps^2, 2)97sage: E.modular_symbols()98Modular Symbols subspace of dimension 2 of Modular Symbols space of dimension 4 and level 13, weight 2, character [zeta6], sign 0, over Cyclotomic Field of order 6 and degree 299100sage: E = EisensteinForms(eps, 1); E101Eisenstein subspace of dimension 1 of Modular Forms space of dimension 1, character [zeta12] and weight 1 over Cyclotomic Field of order 12 and degree 4102sage: E.modular_symbols()103Traceback (most recent call last):104...105ValueError: the weight must be at least 2106"""107try:108return self.__modular_symbols[sign]109except AttributeError:110self.__modular_symbols = {}111except KeyError:112pass113A = self.ambient_module()114S = A.modular_symbols(sign).eisenstein_submodule()115self.__modular_symbols[sign] = S116return S117118class EisensteinSubmodule_params(EisensteinSubmodule):119def parameters(self):120r"""121Return a list of parameters for each Eisenstein series122spanning self. That is, for each such series, return a triple123of the form (`\psi`, `\chi`, level), where `\psi` and `\chi`124are the characters defining the Eisenstein series, and level125is the smallest level at which this series occurs.126127EXAMPLES::128129sage: ModularForms(24,2).eisenstein_submodule().parameters()130[(Dirichlet character modulo 24 of conductor 1 mapping 7 |--> 1, 13 |--> 1, 17 |--> 1, Dirichlet character modulo 24 of conductor 1 mapping 7 |--> 1, 13 |--> 1, 17 |--> 1, 2),131...132Dirichlet character modulo 24 of conductor 1 mapping 7 |--> 1, 13 |--> 1, 17 |--> 1, 24)]133sage: EisensteinForms(12,6).parameters()[-1]134(Dirichlet character modulo 12 of conductor 1 mapping 7 |--> 1, 5 |--> 1, Dirichlet character modulo 12 of conductor 1 mapping 7 |--> 1, 5 |--> 1, 12)135136sage: pars = ModularForms(DirichletGroup(24).0,3).eisenstein_submodule().parameters()137sage: [(x[0].values_on_gens(),x[1].values_on_gens(),x[2]) for x in pars]138[((1, 1, 1), (-1, 1, 1), 1),139((1, 1, 1), (-1, 1, 1), 2),140((1, 1, 1), (-1, 1, 1), 3),141((1, 1, 1), (-1, 1, 1), 6),142((-1, 1, 1), (1, 1, 1), 1),143((-1, 1, 1), (1, 1, 1), 2),144((-1, 1, 1), (1, 1, 1), 3),145((-1, 1, 1), (1, 1, 1), 6)]146sage: EisensteinForms(DirichletGroup(24).0,1).parameters()147[(Dirichlet character modulo 24 of conductor 1 mapping 7 |--> 1, 13 |--> 1, 17 |--> 1, Dirichlet character modulo 24 of conductor 4 mapping 7 |--> -1, 13 |--> 1, 17 |--> 1, 1), (Dirichlet character modulo 24 of conductor 1 mapping 7 |--> 1, 13 |--> 1, 17 |--> 1, Dirichlet character modulo 24 of conductor 4 mapping 7 |--> -1, 13 |--> 1, 17 |--> 1, 2), (Dirichlet character modulo 24 of conductor 1 mapping 7 |--> 1, 13 |--> 1, 17 |--> 1, Dirichlet character modulo 24 of conductor 4 mapping 7 |--> -1, 13 |--> 1, 17 |--> 1, 3), (Dirichlet character modulo 24 of conductor 1 mapping 7 |--> 1, 13 |--> 1, 17 |--> 1, Dirichlet character modulo 24 of conductor 4 mapping 7 |--> -1, 13 |--> 1, 17 |--> 1, 6)]148"""149try:150return self.__parameters151except AttributeError:152char = self._parameters_character()153if char is None:154P = eis_series.compute_eisenstein_params(self.level(), self.weight())155else:156P = eis_series.compute_eisenstein_params(char, self.weight())157self.__parameters = P158return P159160def new_submodule(self, p=None):161r"""162Return the new submodule of self.163164EXAMPLE::165166sage: e = EisensteinForms(Gamma0(225), 2).new_submodule(); e167Modular Forms subspace of dimension 3 of Modular Forms space of dimension 42 for Congruence Subgroup Gamma0(225) of weight 2 over Rational Field168sage: e.basis()169[170q + O(q^6),171q^2 + O(q^6),172q^4 + O(q^6)173]174"""175176if p is not None: raise NotImplementedError177return self.submodule([self(x) for x in self._compute_q_expansion_basis(self.sturm_bound(), new=True)], check=False)178179def _parameters_character(self):180"""181Return the character defining self.182183EXAMPLES::184185sage: EisensteinForms(DirichletGroup(33).1,5)._parameters_character()186Dirichlet character modulo 33 of conductor 11 mapping 23 |--> 1, 13 |--> zeta10187"""188return self.character()189190def change_ring(self, base_ring):191"""192Return self as a module over base_ring.193194EXAMPLES::195196sage: E = EisensteinForms(12,2) ; E197Eisenstein subspace of dimension 5 of Modular Forms space of dimension 5 for Congruence Subgroup Gamma0(12) of weight 2 over Rational Field198sage: E.basis()199[2001 + O(q^6),201q + 6*q^5 + O(q^6),202q^2 + O(q^6),203q^3 + O(q^6),204q^4 + O(q^6)205]206sage: E.change_ring(GF(5))207Eisenstein subspace of dimension 5 of Modular Forms space of dimension 5 for Congruence Subgroup Gamma0(12) of weight 2 over Finite Field of size 5208sage: E.change_ring(GF(5)).basis()209[2101 + O(q^6),211q + q^5 + O(q^6),212q^2 + O(q^6),213q^3 + O(q^6),214q^4 + O(q^6)215]216"""217if base_ring == self.base_ring():218return self219A = self.ambient_module()220B = A.change_ring(base_ring)221return B.eisenstein_submodule()222223def eisenstein_series(self):224"""225Return the Eisenstein series that span this space (over the226algebraic closure).227228EXAMPLES::229230sage: EisensteinForms(11,2).eisenstein_series()231[2325/12 + q + 3*q^2 + 4*q^3 + 7*q^4 + 6*q^5 + O(q^6)233]234sage: EisensteinForms(1,4).eisenstein_series()235[2361/240 + q + 9*q^2 + 28*q^3 + 73*q^4 + 126*q^5 + O(q^6)237]238sage: EisensteinForms(1,24).eisenstein_series()239[240236364091/131040 + q + 8388609*q^2 + 94143178828*q^3 + 70368752566273*q^4 + 11920928955078126*q^5 + O(q^6)241]242sage: EisensteinForms(5,4).eisenstein_series()243[2441/240 + q + 9*q^2 + 28*q^3 + 73*q^4 + 126*q^5 + O(q^6),2451/240 + q^5 + O(q^6)246]247sage: EisensteinForms(13,2).eisenstein_series()248[2491/2 + q + 3*q^2 + 4*q^3 + 7*q^4 + 6*q^5 + O(q^6)250]251252sage: E = EisensteinForms(Gamma1(7),2)253sage: E.set_precision(4)254sage: E.eisenstein_series()255[2561/4 + q + 3*q^2 + 4*q^3 + O(q^4),2571/7*zeta6 - 3/7 + q + (-2*zeta6 + 1)*q^2 + (3*zeta6 - 2)*q^3 + O(q^4),258q + (-zeta6 + 2)*q^2 + (zeta6 + 2)*q^3 + O(q^4),259-1/7*zeta6 - 2/7 + q + (2*zeta6 - 1)*q^2 + (-3*zeta6 + 1)*q^3 + O(q^4),260q + (zeta6 + 1)*q^2 + (-zeta6 + 3)*q^3 + O(q^4)261]262263sage: eps = DirichletGroup(13).0^2264sage: ModularForms(eps,2).eisenstein_series()265[266-7/13*zeta6 - 11/13 + q + (2*zeta6 + 1)*q^2 + (-3*zeta6 + 1)*q^3 + (6*zeta6 - 3)*q^4 - 4*q^5 + O(q^6),267q + (zeta6 + 2)*q^2 + (-zeta6 + 3)*q^3 + (3*zeta6 + 3)*q^4 + 4*q^5 + O(q^6)268]269270sage: M = ModularForms(19,3).eisenstein_subspace()271sage: M.eisenstein_series()272[273]274275sage: M = ModularForms(DirichletGroup(13).0, 1)276sage: M.eisenstein_series()277[278-1/13*zeta12^3 + 6/13*zeta12^2 + 4/13*zeta12 + 2/13 + q + (zeta12 + 1)*q^2 + zeta12^2*q^3 + (zeta12^2 + zeta12 + 1)*q^4 + (-zeta12^3 + 1)*q^5 + O(q^6)279]280281sage: M = ModularForms(GammaH(15, [4]), 4)282sage: M.eisenstein_series()283[2841/240 + q + 9*q^2 + 28*q^3 + 73*q^4 + 126*q^5 + O(q^6),2851/240 + q^3 + O(q^6),2861/240 + q^5 + O(q^6),2871/240 + O(q^6),2881 + q - 7*q^2 - 26*q^3 + 57*q^4 + q^5 + O(q^6),2891 + q^3 + O(q^6),290q + 7*q^2 + 26*q^3 + 57*q^4 + 125*q^5 + O(q^6),291q^3 + O(q^6)292]293"""294try:295return self.__eisenstein_series296except AttributeError:297P = self.parameters()298E = Sequence([element.EisensteinSeries(self.change_ring(chi.base_ring()),299None, t, chi, psi) for \300chi, psi, t in P], immutable=True,301cr = True, universe=Objects())302assert len(E) == self.dimension(), "bug in enumeration of Eisenstein series."303self.__eisenstein_series = E304return E305306def new_eisenstein_series(self):307r"""308Return a list of the Eisenstein series in this space that are new.309310EXAMPLE::311312sage: E = EisensteinForms(25, 4)313sage: E.new_eisenstein_series()314[q + 7*zeta4*q^2 - 26*zeta4*q^3 - 57*q^4 + O(q^6),315q - 9*q^2 - 28*q^3 + 73*q^4 + O(q^6),316q - 7*zeta4*q^2 + 26*zeta4*q^3 - 57*q^4 + O(q^6)]317"""318319return [x for x in self.eisenstein_series() if x.new_level() == self.level()]320321def _compute_q_expansion_basis(self, prec=None, new=False):322"""323Compute a q-expansion basis for self to precision prec.324325EXAMPLES::326327sage: EisensteinForms(22,4)._compute_q_expansion_basis(6)328[1 + O(q^6),329q + 28*q^3 - 8*q^4 + 126*q^5 + O(q^6),330q^2 + 9*q^4 + O(q^6),331O(q^6)]332sage: EisensteinForms(22,4)._compute_q_expansion_basis(15)333[1 + O(q^15),334q + 28*q^3 - 8*q^4 + 126*q^5 + 344*q^7 - 72*q^8 + 757*q^9 - 224*q^12 + 2198*q^13 + O(q^15),335q^2 + 9*q^4 + 28*q^6 + 73*q^8 + 126*q^10 + 252*q^12 + 344*q^14 + O(q^15),336q^11 + O(q^15)]337"""338if prec == None:339prec = self.prec()340else:341prec = rings.Integer(prec)342343if new:344E = self.new_eisenstein_series()345else:346E = self.eisenstein_series()347K = self.base_ring()348V = K**prec349G = []350for e in E:351f = e.q_expansion(prec)352w = f.padded_list(prec)353L = f.base_ring()354if K.has_coerce_map_from(L):355G.append(V(w))356else:357# restrict scalars from L to K358r,d = cyclotomic_restriction(L,K)359s = [r(x) for x in w]360for i in range(d):361G.append(V([x[i] for x in s]))362363W = V.submodule(G, check=False)364R = self._q_expansion_ring()365X = [R(f.list(), prec) for f in W.basis()]366if not new:367return X + [R(0,prec)]*(self.dimension() - len(X))368else:369return X370371def _q_expansion(self, element, prec):372"""373Compute a q-expansion for a given element of self, expressed374as a vector of coefficients for the basis vectors of self,375viewing self as a subspace of the corresponding space of376modular forms.377378EXAMPLES::379380sage: E = EisensteinForms(17,4)381sage: (11*E.0 + 3*E.1).q_expansion(20)38211 + 3*q + 27*q^2 + 84*q^3 + 219*q^4 + 378*q^5 + 756*q^6 + 1032*q^7 + 1755*q^8 + 2271*q^9 + 3402*q^10 + 3996*q^11 + 6132*q^12 + 6594*q^13 + 9288*q^14 + 10584*q^15 + 14043*q^16 + 17379*q^17 + 20439*q^18 + 20580*q^19 + O(q^20)383sage: E._q_expansion([0,0,0,0,11,3],20)38411 + 3*q + 27*q^2 + 84*q^3 + 219*q^4 + 378*q^5 + 756*q^6 + 1032*q^7 + 1755*q^8 + 2271*q^9 + 3402*q^10 + 3996*q^11 + 6132*q^12 + 6594*q^13 + 9288*q^14 + 10584*q^15 + 14043*q^16 + 17379*q^17 + 20439*q^18 + 20580*q^19 + O(q^20)385"""386B = self.q_expansion_basis(prec)387f = self._q_expansion_zero()388for i in range(self._start_position, len(element)):389if element[i] != 0:390f += element[i] * B[i - self._start_position]391return f392393394class EisensteinSubmodule_g0_Q(EisensteinSubmodule_params):395r"""396Space of Eisenstein forms for `\Gamma_0(N)`.397"""398399class EisensteinSubmodule_gH_Q(EisensteinSubmodule_params):400r"""401Space of Eisenstein forms for `\Gamma_H(N)`.402"""403def _parameters_character(self):404"""405Return the character defining self. Since self is406a space of Eisenstein forms on GammaH(N) rather than a space with fixed407character, we return the group GammaH(N) itself.408409EXAMPLES::410411sage: EisensteinForms(GammaH(9, [4]),4)._parameters_character()412Congruence Subgroup Gamma_H(9) with H generated by [4]413"""414return self.group()415416def _convert_matrix_from_modsyms_eis(self, A):417r"""418Given a matrix acting on the space of modular symbols corresponding to419this space, calculate the matrix of the operator it induces on this420space itself. Used for Hecke and diamond operators.421422This is a minor modification of the code used for cusp forms, which is423required because modular symbols "don't see the constant term": the424modular symbol method calculates the matrix of the operator with425respect to the unique basis of the modular forms space for which the426*non-constant* coefficients are in echelon form, and we need to modify427this to get a matrix with respect to the basis we're actually using.428429EXAMPLES::430431sage: EisensteinForms(Gamma1(6), 3).hecke_matrix(3) # indirect doctest432[ 1 0 72 0]433[ 0 0 36 -9]434[ 0 0 9 0]435[ 0 1 -4 10]436"""437from cuspidal_submodule import _convert_matrix_from_modsyms438symbs = self.modular_symbols(sign=0)439d = self.rank()440wrong_mat, pivs = _convert_matrix_from_modsyms(symbs, A)441c = Matrix(self.base_ring(), d, [self.basis()[i][j+1] for i in xrange(d) for j in pivs])442return c * wrong_mat * ~c443444def _compute_hecke_matrix(self, n, bound=None):445r"""446Calculate the matrix of the Hecke operator `T_n` acting on this447space, via modular symbols.448449INPUT:450451- n: a positive integer452453- bound: an integer such that any element of this space with454coefficients a_1, ..., a_b all zero must be the zero455element. If this turns out not to be true, the code will456increase the bound and try again. Setting bound = None is457equivalent to setting bound = self.dimension().458459OUTPUT:460461- a matrix (over `\QQ`)462463ALGORITHM:464465This uses the usual pairing between modular symbols and466modular forms, but in a slightly non-standard way. As for467cusp forms, we can find a basis for this space made up of468forms with q-expansions `c_m(f) = a_{i,j}(T_m)`, where469`T_m` denotes the matrix of the Hecke operator on the470corresponding modular symbols space. Then `c_m(T_n f) =471a_{i,j}(T_n* T_m)`. But we can't find the constant terms472by this method, so an extra step is required.473474EXAMPLE::475476sage: EisensteinForms(Gamma1(6), 3).hecke_matrix(3) # indirect doctest477[ 1 0 72 0]478[ 0 0 36 -9]479[ 0 0 9 0]480[ 0 1 -4 10]481"""482symbs = self.modular_symbols(sign=0)483T = symbs.hecke_matrix(n)484return self._convert_matrix_from_modsyms_eis(T)485486def _compute_diamond_matrix(self, d):487r"""488Calculate the matrix of the diamond bracket operator <d> on this space,489using modular symbols.490491EXAMPLE::492493sage: E = EisensteinForms(Gamma1(7), 3)494sage: E._compute_diamond_matrix(3)495[ 27 126 294 770 2142 3528]496[56/3 85 200 530 1445 2408]497[11/3 14 22 66 233 392]498[ -1 -3 -3 -11 -51 -87]499[ -1 -4 -7 -20 -67 -112]500[-1/3 -2 -6 -15 -34 -56]501"""502symbs = self.modular_symbols(sign=0)503T = symbs.diamond_bracket_matrix(d)504return self._convert_matrix_from_modsyms_eis(T)505506class EisensteinSubmodule_g1_Q(EisensteinSubmodule_gH_Q):507r"""508Space of Eisenstein forms for `\Gamma_1(N)`.509"""510def _parameters_character(self):511"""512Return the character defining self. Since self is a space of Eisenstein513forms on `\Gamma_1(N)`, all characters modulo the level are possible,514so we return the level.515516EXAMPLES::517518sage: EisensteinForms(Gamma1(7),4)._parameters_character()5197520"""521return self.level()522523524class EisensteinSubmodule_eps(EisensteinSubmodule_params):525"""526Space of Eisenstein forms with given Dirichlet character.527528EXAMPLES::529530sage: e = DirichletGroup(27,CyclotomicField(3)).0**2531sage: M = ModularForms(e,2,prec=10).eisenstein_subspace()532sage: M.dimension()5336534535sage: M.eisenstein_series()536[537-1/3*zeta6 - 1/3 + q + (2*zeta6 - 1)*q^2 + q^3 + (-2*zeta6 - 1)*q^4 + (-5*zeta6 + 1)*q^5 + O(q^6),538-1/3*zeta6 - 1/3 + q^3 + O(q^6),539q + (-2*zeta6 + 1)*q^2 + (-2*zeta6 - 1)*q^4 + (5*zeta6 - 1)*q^5 + O(q^6),540q + (zeta6 + 1)*q^2 + 3*q^3 + (zeta6 + 2)*q^4 + (-zeta6 + 5)*q^5 + O(q^6),541q^3 + O(q^6),542q + (-zeta6 - 1)*q^2 + (zeta6 + 2)*q^4 + (zeta6 - 5)*q^5 + O(q^6)543]544sage: M.eisenstein_subspace().T(2).matrix().fcp()545(x + zeta3 + 2) * (x + 2*zeta3 + 1) * (x - 2*zeta3 - 1)^2 * (x - zeta3 - 2)^2546sage: ModularSymbols(e,2).eisenstein_subspace().T(2).matrix().fcp()547(x + zeta3 + 2) * (x + 2*zeta3 + 1) * (x - 2*zeta3 - 1)^2 * (x - zeta3 - 2)^2548549sage: M.basis()550[5511 - 3*zeta3*q^6 + (-2*zeta3 + 2)*q^9 + O(q^10),552q + (5*zeta3 + 5)*q^7 + O(q^10),553q^2 - 2*zeta3*q^8 + O(q^10),554q^3 + (zeta3 + 2)*q^6 + 3*q^9 + O(q^10),555q^4 - 2*zeta3*q^7 + O(q^10),556q^5 + (zeta3 + 1)*q^8 + O(q^10)557]558559"""560# TODO561#def _compute_q_expansion_basis(self, prec):562#B = EisensteinSubmodule_params._compute_q_expansion_basis(self, prec)563#raise NotImplementedError, "must restrict scalars down correctly."564565566from sage.rings.all import CyclotomicField, lcm, euler_phi567568def cyclotomic_restriction(L,K):569r"""570Given two cyclotomic fields L and K, compute the compositum571M of K and L, and return a function and the index [M:K]. The572function is a map that acts as follows (here `M = Q(\zeta_m)`):573574INPUT:575576element alpha in L577578OUTPUT:579580a polynomial `f(x)` in `K[x]` such that `f(\zeta_m) = \alpha`,581where we view alpha as living in `M`. (Note that `\zeta_m`582generates `M`, not `L`.)583584EXAMPLES::585586sage: L = CyclotomicField(12) ; N = CyclotomicField(33) ; M = CyclotomicField(132)587sage: z, n = sage.modular.modform.eisenstein_submodule.cyclotomic_restriction(L,N)588sage: n5892590591sage: z(L.0)592-zeta33^19*x593sage: z(L.0)(M.0)594zeta132^11595596sage: z(L.0^3-L.0+1)597(zeta33^19 + zeta33^8)*x + 1598sage: z(L.0^3-L.0+1)(M.0)599zeta132^33 - zeta132^11 + 1600sage: z(L.0^3-L.0+1)(M.0) - M(L.0^3-L.0+1)6010602"""603if not L.has_coerce_map_from(K):604M = CyclotomicField(lcm(L.zeta_order(), K.zeta_order()))605f = cyclotomic_restriction_tower(M,K)606def g(x):607"""608Function returned by cyclotomic restriction.609610INPUT:611612element alpha in L613614OUTPUT:615616a polynomial `f(x)` in `K[x]` such that `f(\zeta_m) = \alpha`,617where we view alpha as living in `M`. (Note that `\zeta_m`618generates `M`, not `L`.)619620EXAMPLES::621622sage: L = CyclotomicField(12)623sage: N = CyclotomicField(33)624sage: g, n = sage.modular.modform.eisenstein_submodule.cyclotomic_restriction(L,N)625sage: g(L.0)626-zeta33^19*x627"""628return f(M(x))629return g, euler_phi(M.zeta_order())//euler_phi(K.zeta_order())630else:631return cyclotomic_restriction_tower(L,K), \632euler_phi(L.zeta_order())//euler_phi(K.zeta_order())633634635def cyclotomic_restriction_tower(L,K):636"""637Suppose L/K is an extension of cyclotomic fields and L=Q(zeta_m).638This function computes a map with the following property:639640641INPUT:642643an element alpha in L644645OUTPUT:646647a polynomial `f(x)` in `K[x]` such that `f(zeta_m) = alpha`.648649EXAMPLES::650651sage: L = CyclotomicField(12) ; K = CyclotomicField(6)652sage: z = sage.modular.modform.eisenstein_submodule.cyclotomic_restriction_tower(L,K)653sage: z(L.0)654x655sage: z(L.0^2+L.0)656x + zeta6657"""658if not L.has_coerce_map_from(K):659raise ValueError, "K must be contained in L"660f = L.defining_polynomial()661R = K['x']662x = R.gen()663g = R(f)664h_ls = [ t[0] for t in g.factor() if t[0](L.gen(0)) == 0 ]665if len(h_ls) == 0:666raise ValueError, "K (= Q(\zeta_%s)) is not contained in L (= Q(\zeta_%s))"%(K._n(), L._n())667h = h_ls[0]668def z(a):669"""670Function returned by cyclotomic_restriction_tower.671672INPUT:673674an element alpha in L675676OUTPUT:677678a polynomial `f(x)` in `K[x]` such that `f(zeta_m) = alpha`.679680EXAMPLES::681682sage: L = CyclotomicField(121) ; K = CyclotomicField(11)683sage: z = sage.modular.modform.eisenstein_submodule.cyclotomic_restriction_tower(L,K)684sage: z(L.0)685x686sage: z(L.0^11)687zeta11688"""689return R(a.polynomial()) % h690return z691692693694