1 | initial version |
In the past 8 years there have been some changes to SageMath, so it is understandable that this code no longer works. The main issue is that AbelianGroup_class
(now) derives from UniqueRepresentation
, and this puts some limitations on what can be passed to the constructor (i.e. to __init__
). In particular, the arguments should be hashable, so lists (as in the OP from 8 years ago) are not allowed, and should be replaced by tuples. (A way to get around this would be to call the class RayClassGroup_class
, and to define an ordinary function RayClassGroup
that creates instances of it. This is now a common pattern in the SageMath source code, also used with AbelianGroup
.) Also, the constructor of AbelianGroup_class
has changed. Further the custom __call__
method seems to be no longer necessary, and as already mentioned some import statements were missing. Here is the updated class:
from sage.groups.abelian_gps.abelian_group import AbelianGroup_class
from sage.groups.abelian_gps.abelian_group_element import AbelianGroupElement
class RayClassGroup(AbelianGroup_class):
def __init__(self, number_field, mod_ideal = 1, mod_archimedean = None):
if mod_archimedean == None:
mod_archimedean = [0] * len(number_field.real_places())
bnf = gp(number_field.pari_bnf())
# Use PARI to compute ray class group
bnr = bnf.bnrinit([mod_ideal, mod_archimedean], 1)
invariants = bnr[5][2] # bnr.clgp.cyc
invariants = tuple(ZZ(x) for x in invariants)
super().__init__(invariants, names='f')
self.__number_field = number_field
self.__bnr = bnr
def _element_constructor_(self, *args, **kwargs):
if isinstance(args[0], AbelianGroupElement):
return AbelianGroupElement(self, args[0])
else:
I = self.__number_field.ideal(*args, **kwargs)
# Use PARI to compute class of given ideal
g = self.__bnr.bnrisprincipal(I)[1]
g = [ ZZ(x) for x in g ]
return AbelianGroupElement(self, g)
As already mentioned, the constructor should be passed tuples, so the examples become:
sage: K.<a> = NumberField(x^6 + 76*x^4 + 2*x^3 + 2029*x^2 - 158*x + 18955)
sage: G = RayClassGroup(K, K.ideal(3), tuple())
sage: J = K.ideal([5, a^2 + 2*a + 23])
sage: G(J).order()
3
sage: K.<a> = NumberField(x^6 - 3*x^5 - 3*x^4 + 10*x^3 + 3*x^2 - 6*x + 1)
sage: G = RayClassGroup(K, K.ideal(1), (0,1,1,1,1,1)); G
Trivial Abelian group
sage: K.<a> = NumberField(x^6 - 3*x^5 - 3*x^4 + 10*x^3 + 3*x^2 - 6*x + 1)
sage: G = RayClassGroup(K, K.ideal(1), (1,1,1,1,1,1)); G
Multiplicative Abelian group isomorphic to C2
I don't know anything about ray class groups, but based on the original post I assume this is correct.