def is_quotient(M, sym, rank): symbol = GenusSymbol_global_ring(MatrixSpace(ZZ, rank, rank).one()) symbol._local_symbols = [ Genus_Symbol_p_adic_ring(p, syms) for p, syms in sym.iteritems()] s = get_symbol_string(symbol) print s N = FiniteQuadraticModule(s) t = N.order() / M.order() if not Integer(t).is_square(): return False else: t = sqrt(t) for p in Integer(N.order()).prime_factors(): if not N.signature(p) == M.signature(p): return False # if not N.signature() == M.signature(): # return False for G in N.subgroups(): if G.order() == t and G.is_isotropic(): Q = G.quotient() if Q.is_isomorphic(M): print Q return N else: del Q del N return False
def weight_one_half_dim(FQM, use_reduction=True, proof=False, debug=0, local=True): N = Integer(FQM.level()) if not N % 4 == 0: return 0 m = Integer(N / Integer(4)) d = 0 for l in m.divisors(): if is_squarefree(m / l): if debug > 1: print "l = {0}".format(l) TM = FiniteQuadraticModule([2 * l], [-1 / Integer(4 * l)]) if local: dd = [0, 0] # eigenvalue 1, -1 multiplicity for p, n in lcm(FQM.level(), 4 * l).factor(): N = None TN = None J = FQM.jordan_decomposition() L = TM.jordan_decomposition() for j in xrange(1, n + 1): C = J.constituent(p**j)[0] D = L.constituent(p**j)[0] if debug > 1: print "C = {0}, D = {1}".format(C, D) if N == None and C.level() != 1: N = C elif C.level() != 1: N = N + C if TN == None and D.level() != 1: TN = D elif D.level() != 1: TN = TN + D dd1 = invariants_eps(N, TN, use_reduction, proof, debug) if debug > 1: print "dd1 = {}".format(dd1) if dd1 == [0, 0]: # the result is multiplicative # a single [0,0] as a local result # yields [0,0] in the end # and we're done here dd = [0, 0] break if dd == [0, 0]: # this is the first prime dd = dd1 else: # some basic arithmetic ;-) # 1 = 1*1 = (-1)(-1) # -1 = 1*(-1) = (-1)*1 ddtmp = copy(dd) ddtmp[0] = dd[0] * dd1[0] + dd[1] * dd1[1] ddtmp[1] = dd[0] * dd1[1] + dd[1] * dd1[0] dd = ddtmp if debug > 1: print "dd = {0}".format(dd) d += dd[0] else: d += invariants_eps(FQM, TM, use_reduction, proof, debug)[0] return d
def test_dimension_jacobi(N, k): from nils.jacobiforms.dimension_jac_forms import dimension_jac_cusp_forms N = Integer(N) dj = dimension_jac_cusp_forms(k + Integer(1) / Integer(2), N) M = FiniteQuadraticModule([2 * N], [1 / (4 * N)]) s = GenusSymbol(M.jordan_decomposition().genus_symbol()) dv = s.dimension_cusp_forms(k, reduction=True) if not dj == dv: print "Error: ", N, dj, dv return False return True
def weight_one_half_dim(FQM, use_reduction = True, proof = False, debug = 0, local=True): N = Integer(FQM.level()) if not N % 4 == 0: return 0 m = Integer(N/Integer(4)) d = 0 for l in m.divisors(): if is_squarefree(m/l): if debug > 1: print "l = {0}".format(l) TM = FiniteQuadraticModule([2*l],[-1/Integer(4*l)]) if local: dd = [0,0] # eigenvalue 1, -1 multiplicity for p,n in lcm(FQM.level(),4*l).factor(): N = None TN = None J = FQM.jordan_decomposition() L = TM.jordan_decomposition() for j in xrange(1,n+1): C = J.constituent(p**j)[0] D = L.constituent(p**j)[0] if debug > 1: print "C = {0}, D = {1}".format(C,D) if N == None and C.level() != 1: N = C elif C.level() != 1: N = N + C if TN == None and D.level() != 1: TN = D elif D.level() != 1: TN = TN + D dd1 = invariants_eps(N, TN, use_reduction, proof, debug) if debug > 1: print "dd1 = {}".format(dd1) if dd1 == [0,0]: # the result is multiplicative # a single [0,0] as a local result # yields [0,0] in the end # and we're done here dd = [0,0] break if dd == [0,0]: # this is the first prime dd = dd1 else: # some basic arithmetic ;-) # 1 = 1*1 = (-1)(-1) # -1 = 1*(-1) = (-1)*1 ddtmp = copy(dd) ddtmp[0] = dd[0]*dd1[0] + dd[1]*dd1[1] ddtmp[1] = dd[0]*dd1[1] + dd[1]*dd1[0] dd = ddtmp if debug > 1: print "dd = {0}".format(dd) d += dd[0] else: d += invariants_eps(FQM, TM, use_reduction, proof, debug)[0] return d
def compute_simple_shimura_curves(path=''): l = load(path + '/lattices_aniso_1_notgamma0.sobj') simshim = [] aniso_shim_syms = [] for Q in l: M = FiniteQuadraticModule(Q.matrix()) s = GenusSymbol(M.jordan_decomposition().genus_symbol()) aniso_shim_syms.append(s) G = SimpleModulesGraph2n(1, None) G.compute_from_startpoints(aniso_shim_syms) simshim.extend(G._simple) return simshim
def compute_simple_shimura_curves(path=''): l = load(path + '/lattices_aniso_1_notgamma0.sobj') simshim = [] aniso_shim_syms=[] for Q in l: M = FiniteQuadraticModule(Q.matrix()) s = GenusSymbol(M.jordan_decomposition().genus_symbol()) aniso_shim_syms.append(s) G = SimpleModulesGraph2n(1,None) G.compute_from_startpoints(aniso_shim_syms) simshim.extend(G._simple) return simshim
def __init__(self, A, use_genus_symbols=False, aniso_formula=False, use_reduction=False): try: from sfqm.fqm.genus_symbol import GenusSymbol except ImportError as e: print(e) use_genus_symbols = False print("Not using genus symbols.") self._use_reduction = use_reduction if use_genus_symbols: if isinstance(A, str): g = GenusSymbol(A) else: try: g = GenusSymbol(A.jordan_decomposition().genus_symbol()) except: raise ValueError self._g = g n2 = self._n2 = g.torsion(2) self._v2 = g.two_torsion_values() self._M = None self._aniso_formula = aniso_formula else: self._M = FiniteQuadraticModule(A) self._g = None self._level = self._M.level() self._aniso_formula = False if is_odd(self._M.order()): self._n2 = n2 = 1 self._v2 = {0: 1} else: self._M2 = M2 = self._M.kernel_subgroup(2).as_ambient()[0] self._n2 = n2 = self._M2.order() self._v2 = list(self._M2.values()) if use_genus_symbols: self._signature = g.signature() m = g.order() else: self._signature = self._M.signature() m = self._M.order() self._m = m d = Integer(1) / Integer(2) * (m + n2) # |discriminant group/{+/-1}| self._d = d self._alpha3 = None self._alpha4 = None
def test_list_freitag(m=-1): all = True if m == -1 else False for n, symbols in list_freitag.items(): if all or n == m: for symbol in symbols: M = FiniteQuadraticModule(symbol) V = VectorValuedModularForms(M) k = Integer(2 + n) / Integer(2) glob = is_global(M, 2, n) if glob: d = V.dimension_cusp_forms(k) else: d = "?" print("n = {0} {1}: Dimension({2}) = {3}, {4}, |M|={5}".format( n, symbol, str(k), d, glob, M.order()))
def test_list_freitag(m=-1): all = True if m == -1 else False for n, symbols in list_freitag.iteritems(): if all or n == m: for symbol in symbols: M = FiniteQuadraticModule(symbol) V = VectorValuedModularForms(M) k = Integer(2 + n) / Integer(2) glob = is_global(M, 2, n) if glob: d = V.dimension_cusp_forms(k) else: d = "?" print "n = ", n, " ", symbol, ': Dimension(' + str( k) + ') = ', d, ", ", glob, '|M|=', M.order()
def is_simple(symstr): M = FiniteQuadraticModule(symstr) V = VectorValuedModularForms(M) d = V.dimension_cusp_forms(V.weight()) if d == 0: return True else: return False
def is_quotient(M, sym, rank): symbol = GenusSymbol_global_ring(MatrixSpace(ZZ, rank, rank).one()) symbol._local_symbols = [ Genus_Symbol_p_adic_ring(p, syms) for p, syms in sym.iteritems() ] s = get_symbol_string(symbol) print s N = FiniteQuadraticModule(s) t = N.order() / M.order() if not Integer(t).is_square(): return False else: t = sqrt(t) for p in N.order().prime_factors(): if not N.signature(p) == M.signature(p): return False #if not N.signature() == M.signature(): # return False for G in N.subgroups(): if G.order() == t and G.is_isotropic(): Q = G.quotient() if Q.is_isomorphic(M): print Q return N.jordan_decomposition().genus_symbol() else: del (Q) del (N) return False
def Bbf(M, m): # brute force algorithm if isinstance(M, str): M = FiniteQuadraticModule(M) rank = len(M.gens()) + 2 sign = M.signature() symbols = all_symbols(sign, rank, M.order() * m ** 2) B = list(is_quotient([(M, sym, rank) for sym in symbols])) B = filter(lambda x: x[1] != False, B) B = map(lambda x: x[1], B) modules = Set(B) modules_unique = list() for M in modules: seen = False for N in modules_unique: if N.is_isomorphic(M): seen = True if not seen: modules_unique.append(M) return [M.jordan_decomposition().genus_symbol() for M in modules_unique]
def is_simple(symstr, k): if not symstr == '': M = FiniteQuadraticModule(symstr) V = VectorValuedModularForms(M) d = V.dimension_cusp_forms(k) else: d = dimension_cusp_forms(1, k) if d == 0: return True else: return False
def Bbf(M, m): #brute force algorithm if isinstance(M, str): M = FiniteQuadraticModule(M) rank = len(M.gens()) + 2 sign = M.signature() symbols = all_symbols(sign, rank, M.order() * m**2) B = list(is_quotient([(M, sym, rank) for sym in symbols])) B = filter(lambda x: x[1] != False, B) B = map(lambda x: GenusSymbol(x[1]), B) modules = Set(B) print modules modules_unique = list() for M in modules: seen = False for N in modules_unique: if N.defines_isomorphic_module(M): seen = True if not seen: modules_unique.append(M) return modules_unique
def reps(l): simple_dict = dict() mods_seen = list() for s in simple: if not s == '': M = FiniteQuadraticModule(s) else: M = FiniteQuadraticModule() if not simple_dict.has_key(M.level()): simple_dict[M.level()] = list() add = True for N in mods_seen: if M.level() == N.level() and M.is_isomorphic(N): add = False if add: simple_dict[M.level()].append(s) mods_seen.append(M) return simple_dict
def test_list_freitag(m=-1): all=True if m==-1 else False for n,symbols in list_freitag.iteritems(): if all or n==m: for symbol in symbols: M=FiniteQuadraticModule(symbol) V=VectorValuedModularForms(M) k = Integer(2+n)/Integer(2) glob = is_global(M,2,n) if glob: d=V.dimension_cusp_forms(k) else: d="?" print "n = ", n, " ", symbol, ': Dimension('+ str(k) + ') = ', d, ", ", glob, '|M|=', M.order()
def compare_spaces(n, min_D, max_D): spaces = dict() rank = 2 + n sign = 2 - n k = Integer(2 + n) / Integer(2) bad_symbols = dict() for D in range(min_D, max_D + 1): global_symbols = search_global_symbols(n, D) #global_symbols=Set(global_symbols) if len(global_symbols) > 0: print("Symbols for D ={0} : {1}".format(D, len(global_symbols))) for sym in global_symbols: symstr = get_symbol_string(sym) print(symstr) sys.stdout.flush() M = FiniteQuadraticModule(symstr) V = VectorValuedModularForms(M) dv, ds, S, B = compare_vv_scalar(V, k) if dv == 0 and ds != 0 or dv != 0: print( "dim S({0},{1},rho*) = {2}, dim S(Gamma0({3}),chi_D,{1})={4}" .format(symstr, k, dv, V._level, ds)) if ds != 0: W = V._W f, index = find_lifting_candidate(W, B) #spaces[D]={"W": W, "dimW": dv, "S": S, "dimS":ds, "new_lifting_candidate": f and f.is_new()} if f: #and f.is_new: print("Newform lifting candidate: {0} \n index={1}". format(f.qexp(index + 3), index)) #elif f: # print "Oldform lifting candidate found." else: print("**** No newform lifting candidate") if V._level not in bad_symbols: bad_symbols[V._level] = list() bad_symbols[V._level].append(symstr) #else: # print "No lifting candidate, basis:" # S elif dv == 0: if V._level not in bad_symbols: bad_symbols[V._level] = list() bad_symbols[V._level].append(symstr) else: if dv == 0 and ds == 0: print("simple and scalar valued space = 0") return bad_symbols
def anisotropic_symbols(N, sig): syms = [] if N == 1 and sig % 8 == 0: return prime_anisotropic_symbols(1) for p, n in Integer(N).factor(): print p, n if len(syms) == 0: syms = prime_anisotropic_symbols(p**n) print syms else: syms_old = deepcopy(syms) syms = list() for r in itertools.product(syms_old, prime_anisotropic_symbols(p**n)): syms.append(r[0] + '.' + r[1]) print syms if len(syms) == 0: return [] print syms syms_new = list() for s in syms: print s if (FiniteQuadraticModule(s).signature()) % 8 == sig: syms_new.append(s) return syms_new
def B(M, m, algorithm='theorem', rec=True, dict=False): if algorithm == 'bf': return Bbf(M, m) elif not algorithm == 'theorem': raise ValueError( 'algorithm has to be one of "theorem" and "bf" (for brute force)') Bs = list() if not is_prime(m): raise ValueError('m is supposed to be prime (general case: TODO)') p = m if isinstance(M, FiniteQuadraticModule_ambient): sym_M = genus_symbol_string_to_dict( M.jordan_decomposition().genus_symbol()) elif isinstance(M, str): if len(M) > 0: sym_M = genus_symbol_string_to_dict(M) else: sym_M = {} else: raise ValueError('M needs to be a "FiniteQuadraticModule" or a "str".') if not sym_M.has_key(p): sym_M[p] = list() #print sym_M #sym_M = get_genus_symbol_dict(M) if p == 2: sym_new = deepcopy(sym_M) sym_new[p].append([1, 2, 7, 0, 0]) Bs.append(sym_new) print sym_new, dict_to_genus_symbol_string(sym_new) sym_new = deepcopy(sym_M) sym_new[p].append([1, 2, 7, 1, 0]) Bs.append(sym_new) print sym_new, dict_to_genus_symbol_string(sym_new) for s in sym_M[p]: print s t = s[3] print t if rec: for ss in sym_M[p]: if t == 1 and ss[0] == s[0] + 1: sym_new = deepcopy(sym_M) sym_new[p].remove(s) if s[2] in [1, 5]: s2n = s[2] + 2 else: s2n = s[2] - 2 sym_new[p].append( [s[0], s[1], s2n, s[3], (s[4] + 2) % 8]) sym_new[p].remove(ss) if ss[2] in [1, 5]: ss2n = ss[2] + 2 else: ss2n = ss[2] - 2 sym_new[p].append( [ss[0], ss[1], ss2n, ss[3], (ss[4] + 2) % 8]) Br = B(dict_to_genus_symbol_string(sym_new), p, rec=False, dict=True) print "Br=", B(dict_to_genus_symbol_string(sym_new), p, rec=False, dict=True) Bs = Bs + Br if s[1] > 2 or t == 0 or t == None: # q^+2 type II -> (2q)^+2 type II if s[1] > 2 or s[4] == 0: print "rule q^+2 -> (2q)^+2" sym_new = deepcopy(sym_M) sym_new[p].remove(s) sym_new[p].append([s[0] + 1, 2, 7, 0, 0]) if s[1] > 2: sym_new[p].append([s[0], s[1] - 2, -s[2], s[3], s[4]]) Bs.append(sym_new) print dict_to_genus_symbol_string(sym_new) # q^-2 -> (2q)_4^-2 if s[1] > 2 or s[4] == 4: print "rule q^-2 -> (2q)_4^-2" sym_new = deepcopy(sym_M) sym_new[p].remove(s) sym_new[p].append([s[0] + 1, 2, 3, 1, 4]) if s[1] > 2: sym_new[p].append([ s[0], s[1] - 2, (s[2] * 3) % 8, s[3], (s[4] + 4) % 8 ]) Bs.append(sym_new) print sym_new, dict_to_genus_symbol_string(sym_new) # q^+2 -> (2q)_0^+2 if s[1] > 2 or s[4] == 0: print "rule q^+2 -> (2q)_0^+2" sym_new = deepcopy(sym_M) sym_new[p].remove(s) sym_new[p].append([s[0] + 1, 2, 7, 1, 0]) if s[1] > 2: sym_new[p].append([s[0], s[1] - 2, -s[2], s[3], s[4]]) Bs.append(sym_new) print dict_to_genus_symbol_string(sym_new) if t == 1: print "t=1" #rule for odd type, mult 1 power up odds = [1, 3, 5, 7] for o in odds: if (s[1] == 1 and (s[4]==o or s[0]==1 and s[4] % 8 == (o+4) %8)) \ or s[1]>3 \ or (s[1]==3 and not ((s[4]-o) % 8 ) in [4,6] and kronecker(s[2]*o,2) % 8 == 1) \ or (s[1]==2 and (s[4]-o) % 8 in odds): sym_new = deepcopy(sym_M) sym_new[p].remove(s) sym_new[p].append([s[0] + 2, 1, o, 1, o]) if s[1] > 1: sym_new[p].append( [s[0], s[1] - 1, s[2] * o, 1, (s[4] - o) % 8]) print dict_to_genus_symbol_string(sym_new) Bs.append(sym_new) print s[1] if s[1] >= 2: print s if s[4] == 0 or (s[0] == 1 and s[4] == 4): print "1,4" print sym_M sym_new = deepcopy(sym_M) sym_new[p].remove(s) sym_new[p].append([s[0] + 1, 2, 7, 0, 0]) if s[1] > 2: sym_new[p].append( [s[0], s[1] - 2, (-s[2]) % 8, 1, s[4]]) Bs.append(sym_new) print sym_new print dict_to_genus_symbol_string(sym_new) if s[4] == 4: sym_new = deepcopy(sym_M) sym_new[p].remove(s) sym_new[p].append([s[0] + 1, 2, 3, 0, 4]) if s[1] > 2: sym_new[p].append([ s[0], s[1] - 2, (s[2] * 3) % 8, 1, (s[4] - 4) % 8 ]) Bs.append(sym_new) print sym_new if s[1] > 2 and s[1] % 2 == 0: sym_new = deepcopy(sym_M) sym_new[p].remove(s) sym_new[p].append([s[0] + 1, 2, s[2], 0, s[4]]) sym_new[p].append([s[0], s[1] - 2, 0, 0, 0]) Bs.append(sym_new) else: ep = -1 if p % 4 == 3 else 1 if not sym_M.has_key(p): sym_M[p] = list() #rule 1+2 for triv p-module sym_new = deepcopy(sym_M) sym_new[p].append([2, 1, 1]) Bs.append(sym_new) sym_new = deepcopy(sym_M) sym_new[p].append([2, 1, -1]) Bs.append(sym_new) sym_new = deepcopy(sym_M) sym_new[p].append([1, 2, ep]) Bs.append(sym_new) for s in sym_M[p]: sym_new = deepcopy(sym_M) sym_new[p].remove(s) #rule 1 (power+2, mult 1) sym_new[p].append([s[0] + 2, 1, s[2]]) if s[1] > 1: sym_new[p].append([s[0], s[1] - 1, 1]) Bs.append(sym_new) sym_new = deepcopy(sym_M) sym_new[p].remove(s) sym_new[p].append([s[0] + 2, 1, -s[2]]) sym_new[p].append([s[0], s[1] - 1, -1]) Bs.append(sym_new) else: Bs.append(sym_new) #rule 2 (power+1, mult 2) if s[1] >= 2: if s[1] == 2 and s[2] == ep: sym_new = deepcopy(sym_M) sym_new[p].remove(s) sym_new[p].append([s[0] + 1, 2, ep]) Bs.append(sym_new) elif s[1] > 2: sym_new = deepcopy(sym_M) sym_new[p].remove(s) sym_new[p].append([s[0] + 1, 2, ep]) sym_new[p].append([s[0], s[1] - 2, ep * s[2]]) Bs.append(sym_new) if dict: return Bs Bss = list() for sym in Bs: sym = reduce_symbol(sym) sym = dict_to_genus_symbol_string(sym) Bss.append(sym) if p == 2: Bs = list() for s in Bss: try: FiniteQuadraticModule(s) Bs.append(s) except: print "ERROR: ", s Bss = Bs print "Bs = ", Bs #mods_uniq=list() #for M in mods: # seen = False # for N in mods_uniq: # if N.is_isomorphic(M): # seen = True # if not seen: # mods_uniq.append(M) #Bss = [M.jordan_decomposition().genus_symbol() for M in mods_uniq] return Bss
class VectorValuedModularForms(SageObject): r""" Class representing a space of vector valued modular forms transforming with the Weil representation of a discriminant module. EXAMPLES: As input we use any input that one can use for a finite quadratic module. (For instance a genus symbol.) :: sage: V=VectorValuedModularForms('2_7^+1.3^-2') sage: V Vector valued modular forms for the Weil representation corresponding to: Finite quadratic module in 3 generators: gens: e0, e1, e2 form: 3/4*x0^2 + 2/3*x1^2 + 1/3*x2^2 SEE ALSO: :class:`psage.modules.finite_quadratic_modules.FiniteQuadraticModule` """ def __init__(self, A, use_genus_symbols=False, aniso_formula=False, use_reduction=False): try: from sfqm.fqm.genus_symbol import GenusSymbol except ImportError, e: print e use_genus_symbols = False print "Not using genus symbols." self._use_reduction = use_reduction if use_genus_symbols: if isinstance(A, str): g = GenusSymbol(A) else: try: g = GenusSymbol(A.jordan_decomposition().genus_symbol()) except: raise ValueError self._g = g n2 = self._n2 = g.torsion(2) self._v2 = g.two_torsion_values() self._M = None self._aniso_formula = aniso_formula else: self._M = FiniteQuadraticModule(A) self._g = None self._level = self._M.level() self._aniso_formula = False if is_odd(self._M.order()): self._n2 = n2 = 1 self._v2 = {0: 1} else: self._M2 = M2 = self._M.kernel_subgroup(2).as_ambient()[0] self._n2 = n2 = self._M2.order() self._v2 = self._M2.values() if use_genus_symbols: self._signature = g.signature() m = g.order() else: self._signature = self._M.signature() m = self._M.order() self._m = m d = Integer(1) / Integer(2) * (m + n2) # |discriminant group/{+/-1}| self._d = d self._alpha3 = None self._alpha4 = None
class VectorValuedModularForms(SageObject): r""" Class representing a space of vector valued modular forms transforming with the Weil representation of a discriminant module. EXAMPLES: As input we use any input that one can use for a finite quadratic module. (For instance a genus symbol.) :: sage: V=VectorValuedModularForms('2_7^+1.3^-2') sage: V Vector valued modular forms for the Weil representation corresponding to: Finite quadratic module in 3 generators: gens: e0, e1, e2 form: 3/4*x0^2 + 2/3*x1^2 + 1/3*x2^2 SEE ALSO: :class:`psage.modules.finite_quadratic_modules.FiniteQuadraticModule` """ def __init__(self, A, use_genus_symbols=False, aniso_formula=False, use_reduction=False): try: from sfqm.fqm.genus_symbol import GenusSymbol except ImportError as e: print(e) use_genus_symbols = False print("Not using genus symbols.") self._use_reduction = use_reduction if use_genus_symbols: if isinstance(A, str): g = GenusSymbol(A) else: try: g = GenusSymbol(A.jordan_decomposition().genus_symbol()) except: raise ValueError self._g = g n2 = self._n2 = g.torsion(2) self._v2 = g.two_torsion_values() self._M = None self._aniso_formula = aniso_formula else: self._M = FiniteQuadraticModule(A) self._g = None self._level = self._M.level() self._aniso_formula = False if is_odd(self._M.order()): self._n2 = n2 = 1 self._v2 = {0: 1} else: self._M2 = M2 = self._M.kernel_subgroup(2).as_ambient()[0] self._n2 = n2 = self._M2.order() self._v2 = list(self._M2.values()) if use_genus_symbols: self._signature = g.signature() m = g.order() else: self._signature = self._M.signature() m = self._M.order() self._m = m d = Integer(1) / Integer(2) * (m + n2) # |discriminant group/{+/-1}| self._d = d self._alpha3 = None self._alpha4 = None def __repr__(self): return "Vector valued modular forms for the Weil representation corresponding to: \n" + self._M.__repr__( ) def finite_quadratic_module(self): return self._M def dimension(self, k, ignore=False, debug=0): if k < 2 and not ignore: raise NotImplementedError("k has to >= 2") s = self._signature if not (2 * k in ZZ): raise ValueError("k has to be integral or half-integral") if (2 * k + s) % 4 != 0 and not ignore: raise NotImplementedError( "2k has to be congruent to -signature mod 4") if 0 in self._v2: v2 = self._v2[0] else: v2 = 1 if self._g != None: if not self._aniso_formula: vals = list(self._g.values()) #else: #print "using aniso_formula" M = self._g else: vals = list(self._M.values()) M = self._M prec = ceil(max(log(M.order(), 2), 52) + 1) + 17 #print prec RR = RealField(prec) CC = ComplexField(prec) d = self._d m = self._m if debug > 0: print(d, m) if self._alpha3 == None: if self._aniso_formula: self._alpha4 = 1 self._alpha3 = -sum( [BB(a) * mm for a, mm in self._v2.items() if a != 0]) #print self._alpha3 self._alpha3 += Integer(d) - Integer( 1) - self._g.beta_formula() #print self._alpha3, self._g.a5prime_formula() self._alpha3 = self._alpha3 / RR(2) else: self._alpha3 = sum([(1 - a) * mm for a, mm in self._v2.items() if a != 0]) #print self._alpha3 self._alpha3 += sum([(1 - a) * mm for a, mm in vals.items() if a != 0]) #print self._alpha3 self._alpha3 = self._alpha3 / Integer(2) self._alpha4 = 1 / Integer(2) * ( vals[0] + v2) # the codimension of SkL in MkL alpha3 = self._alpha3 alpha4 = self._alpha4 if debug > 0: print(alpha3, alpha4) g1 = M.char_invariant(1) g1 = CC(g1[0] * g1[1]) #print g1 g2 = M.char_invariant(2) g2 = RR(real(g2[0] * g2[1])) if debug > 0: print(g2, g2.parent()) g3 = M.char_invariant(-3) g3 = CC(g3[0] * g3[1]) if debug > 0: print( RR(d) / RR(4), sqrt(RR(m)) / RR(4), CC(exp(2 * CC.pi() * CC(0, 1) * (2 * k + s) / Integer(8)))) alpha1 = RR(d) / RR(4) - (sqrt(RR(m)) / RR(4) * CC( exp(2 * CC.pi() * CC(0, 1) * (2 * k + s) / Integer(8))) * g2) if debug > 0: print(alpha1) alpha2 = RR(d) / RR(3) + sqrt(RR(m)) / (3 * sqrt(RR(3))) * real( exp(CC(2 * CC.pi() * CC(0, 1) * (4 * k + 3 * s - 10) / 24)) * (g1 + g3)) if debug > 0: print(alpha1, alpha2, g1, g2, g3, d, k, s) dim = real(d + (d * k / Integer(12)) - alpha1 - alpha2 - alpha3) if debug > 0: print("dimension:", dim) if abs(dim - round(dim)) > 1e-6: raise RuntimeError( "Error ({0}) too large in dimension formula for {1} and k={2}". format(abs(dim - round(dim)), self._M if self._M is not None else self._g, k)) dimr = dim dim = Integer(round(dim)) if k >= 2 and dim < 0: raise RuntimeError("Negative dimension (= {0}, {1})!".format( dim, dimr)) return dim def dimension_cusp_forms(self, k, ignore=False, no_inv=False, test_positive=False, proof=False, debug=1): if debug > 0: if self._g is not None: print("Computing dimension for {}".format(self._g)) else: print("Computing dimension for {}".format(self._M)) if k == Integer(3) / 2: dim = self.dimension(k, True, debug=debug) - self._alpha4 if not test_positive or dim <= 0: if self._M == None: self._M = self._g.finite_quadratic_module() corr = weight_one_half_dim(self._M, self._use_reduction, proof=proof) if debug > 0: print("weight one half: {0}".format(corr)) dim += corr else: dim = self.dimension(k, ignore, debug=debug) - self._alpha4 if k == Integer(2) and not no_inv: if test_positive and dim > 0: return dim if self._M == None: self._M = self._g.finite_quadratic_module() if self._M.level() == 1: return dim + 1 dinv = cython_invariants_dim(self._M, self._use_reduction) dim = dim + dinv if dim < 0: raise RuntimeError( "Negative dimension (= {0}, alpha4 = {1})!".format( dim, self._alpha4)) return dim
def FQM(self): return FiniteQuadraticModule(self._genus_symbol)