Class groups of number fields

An element of a class group is stored as a pair consisting of both an explicit ideal in that ideal class, and a list of exponents giving that ideal class in terms of the generators of the parent class group. These can be accessed with the ideal() and exponents() methods respectively.

EXAMPLES:

sage: x = polygen(ZZ, 'x')
sage: K.<a> = NumberField(x^2 + 23)
sage: I = K.class_group().gen(); I
Fractional ideal class (2, 1/2*a - 1/2)
sage: I.ideal()
Fractional ideal (2, 1/2*a - 1/2)
sage: I.exponents()
(1,)

sage: I.ideal() * I.ideal()
Fractional ideal (4, 1/2*a + 3/2)
sage: (I.ideal() * I.ideal()).reduce_equiv()
Fractional ideal (2, 1/2*a + 1/2)
sage: J = I * I; J    # class group multiplication is automatically reduced
Fractional ideal class (2, 1/2*a + 1/2)
sage: J.ideal()
Fractional ideal (2, 1/2*a + 1/2)
sage: J.exponents()
(2,)

sage: I * I.ideal()   # ideal classes coerce to their representative ideal
Fractional ideal (4, 1/2*a + 3/2)

sage: K.fractional_ideal([2, 1/2*a + 1/2])
Fractional ideal (2, 1/2*a + 1/2)
sage: K.fractional_ideal([2, 1/2*a + 1/2]).is_principal()
False
sage: K.fractional_ideal([2, 1/2*a + 1/2])^3
Fractional ideal (1/2*a - 3/2)
>>> from sage.all import *
>>> x = polygen(ZZ, 'x')
>>> K = NumberField(x**Integer(2) + Integer(23), names=('a',)); (a,) = K._first_ngens(1)
>>> I = K.class_group().gen(); I
Fractional ideal class (2, 1/2*a - 1/2)
>>> I.ideal()
Fractional ideal (2, 1/2*a - 1/2)
>>> I.exponents()
(1,)

>>> I.ideal() * I.ideal()
Fractional ideal (4, 1/2*a + 3/2)
>>> (I.ideal() * I.ideal()).reduce_equiv()
Fractional ideal (2, 1/2*a + 1/2)
>>> J = I * I; J    # class group multiplication is automatically reduced
Fractional ideal class (2, 1/2*a + 1/2)
>>> J.ideal()
Fractional ideal (2, 1/2*a + 1/2)
>>> J.exponents()
(2,)

>>> I * I.ideal()   # ideal classes coerce to their representative ideal
Fractional ideal (4, 1/2*a + 3/2)

>>> K.fractional_ideal([Integer(2), Integer(1)/Integer(2)*a + Integer(1)/Integer(2)])
Fractional ideal (2, 1/2*a + 1/2)
>>> K.fractional_ideal([Integer(2), Integer(1)/Integer(2)*a + Integer(1)/Integer(2)]).is_principal()
False
>>> K.fractional_ideal([Integer(2), Integer(1)/Integer(2)*a + Integer(1)/Integer(2)])**Integer(3)
Fractional ideal (1/2*a - 3/2)
class sage.rings.number_field.class_group.ClassGroup(gens_orders, names, number_field, gens, proof=True)[source]

Bases: AbelianGroupWithValues_class

The class group of a number field.

EXAMPLES:

sage: x = polygen(ZZ, 'x')
sage: K.<a> = NumberField(x^2 + 23)
sage: G = K.class_group(); G
Class group of order 3 with structure C3 of
 Number Field in a with defining polynomial x^2 + 23
sage: G.category()
Category of finite enumerated commutative groups
>>> from sage.all import *
>>> x = polygen(ZZ, 'x')
>>> K = NumberField(x**Integer(2) + Integer(23), names=('a',)); (a,) = K._first_ngens(1)
>>> G = K.class_group(); G
Class group of order 3 with structure C3 of
 Number Field in a with defining polynomial x^2 + 23
>>> G.category()
Category of finite enumerated commutative groups

Note the distinction between abstract generators, their ideal, and exponents:

sage: C = NumberField(x^2 + 120071, 'a').class_group(); C
Class group of order 500 with structure C250 x C2
of Number Field in a with defining polynomial x^2 + 120071
sage: c = C.gen(0)
sage: c  # random
Fractional ideal class (5, 1/2*a + 3/2)
sage: c.ideal()  # random
Fractional ideal (5, 1/2*a + 3/2)
sage: c.ideal() is c.value()   # alias
True
sage: c.exponents()
(1, 0)
>>> from sage.all import *
>>> C = NumberField(x**Integer(2) + Integer(120071), 'a').class_group(); C
Class group of order 500 with structure C250 x C2
of Number Field in a with defining polynomial x^2 + 120071
>>> c = C.gen(Integer(0))
>>> c  # random
Fractional ideal class (5, 1/2*a + 3/2)
>>> c.ideal()  # random
Fractional ideal (5, 1/2*a + 3/2)
>>> c.ideal() is c.value()   # alias
True
>>> c.exponents()
(1, 0)
Element[source]

alias of FractionalIdealClass

gens_ideals()[source]

Return generating ideals for the (\(S\)-)class group.

This is an alias for gens_values().

OUTPUT: a tuple of ideals, one for each abstract Abelian group generator

EXAMPLES:

sage: x = polygen(ZZ, 'x')
sage: K.<a> = NumberField(x^4 + 23)
sage: K.class_group().gens_ideals()   # random gens (platform dependent)
(Fractional ideal (2, 1/4*a^3 - 1/4*a^2 + 1/4*a - 1/4),)

sage: C = NumberField(x^2 + x + 23899, 'a').class_group(); C
Class group of order 68 with structure C34 x C2 of Number Field
in a with defining polynomial x^2 + x + 23899
sage: C.gens()
(Fractional ideal class (7, a + 5), Fractional ideal class (5, a + 3))
sage: C.gens_ideals()
(Fractional ideal (7, a + 5), Fractional ideal (5, a + 3))
>>> from sage.all import *
>>> x = polygen(ZZ, 'x')
>>> K = NumberField(x**Integer(4) + Integer(23), names=('a',)); (a,) = K._first_ngens(1)
>>> K.class_group().gens_ideals()   # random gens (platform dependent)
(Fractional ideal (2, 1/4*a^3 - 1/4*a^2 + 1/4*a - 1/4),)

>>> C = NumberField(x**Integer(2) + x + Integer(23899), 'a').class_group(); C
Class group of order 68 with structure C34 x C2 of Number Field
in a with defining polynomial x^2 + x + 23899
>>> C.gens()
(Fractional ideal class (7, a + 5), Fractional ideal class (5, a + 3))
>>> C.gens_ideals()
(Fractional ideal (7, a + 5), Fractional ideal (5, a + 3))
number_field()[source]

Return the number field that this (\(S\)-)class group is attached to.

EXAMPLES:

sage: x = polygen(ZZ, 'x')
sage: C = NumberField(x^2 + 23, 'w').class_group(); C
Class group of order 3 with structure C3 of
 Number Field in w with defining polynomial x^2 + 23
sage: C.number_field()
Number Field in w with defining polynomial x^2 + 23

sage: K.<a> = QuadraticField(-14)
sage: CS = K.S_class_group(K.primes_above(2))
sage: CS.number_field()
Number Field in a with defining polynomial x^2 + 14 with a = 3.741657386773942?*I
>>> from sage.all import *
>>> x = polygen(ZZ, 'x')
>>> C = NumberField(x**Integer(2) + Integer(23), 'w').class_group(); C
Class group of order 3 with structure C3 of
 Number Field in w with defining polynomial x^2 + 23
>>> C.number_field()
Number Field in w with defining polynomial x^2 + 23

>>> K = QuadraticField(-Integer(14), names=('a',)); (a,) = K._first_ngens(1)
>>> CS = K.S_class_group(K.primes_above(Integer(2)))
>>> CS.number_field()
Number Field in a with defining polynomial x^2 + 14 with a = 3.741657386773942?*I
class sage.rings.number_field.class_group.FractionalIdealClass(parent, element, ideal=None)[source]

Bases: AbelianGroupWithValuesElement

A fractional ideal class in a number field.

EXAMPLES:

sage: x = polygen(ZZ, 'x')
sage: G = NumberField(x^2 + 23,'a').class_group(); G
Class group of order 3 with structure C3 of
 Number Field in a with defining polynomial x^2 + 23
sage: I = G.0; I
Fractional ideal class (2, 1/2*a - 1/2)
sage: I.ideal()
Fractional ideal (2, 1/2*a - 1/2)

sage: K.<w> = QuadraticField(-23)
sage: OK = K.ring_of_integers()
sage: C = OK.class_group()
sage: P2a, P2b = [P for P, e in (2*K).factor()]
sage: c = C(P2a); c
Fractional ideal class (2, 1/2*w - 1/2)
sage: c.gens()
(2, 1/2*w - 1/2)
>>> from sage.all import *
>>> x = polygen(ZZ, 'x')
>>> G = NumberField(x**Integer(2) + Integer(23),'a').class_group(); G
Class group of order 3 with structure C3 of
 Number Field in a with defining polynomial x^2 + 23
>>> I = G.gen(0); I
Fractional ideal class (2, 1/2*a - 1/2)
>>> I.ideal()
Fractional ideal (2, 1/2*a - 1/2)

>>> K = QuadraticField(-Integer(23), names=('w',)); (w,) = K._first_ngens(1)
>>> OK = K.ring_of_integers()
>>> C = OK.class_group()
>>> P2a, P2b = [P for P, e in (Integer(2)*K).factor()]
>>> c = C(P2a); c
Fractional ideal class (2, 1/2*w - 1/2)
>>> c.gens()
(2, 1/2*w - 1/2)
gens()[source]

Return generators for a representative ideal in this (\(S\)-)ideal class.

EXAMPLES:

sage: K.<w> = QuadraticField(-23)
sage: OK = K.ring_of_integers()
sage: C = OK.class_group()
sage: P2a, P2b = [P for P, e in (2*K).factor()]
sage: c = C(P2a); c
Fractional ideal class (2, 1/2*w - 1/2)
sage: c.gens()
(2, 1/2*w - 1/2)
>>> from sage.all import *
>>> K = QuadraticField(-Integer(23), names=('w',)); (w,) = K._first_ngens(1)
>>> OK = K.ring_of_integers()
>>> C = OK.class_group()
>>> P2a, P2b = [P for P, e in (Integer(2)*K).factor()]
>>> c = C(P2a); c
Fractional ideal class (2, 1/2*w - 1/2)
>>> c.gens()
(2, 1/2*w - 1/2)
ideal()[source]

Return a representative ideal in this ideal class.

EXAMPLES:

sage: K.<w> = QuadraticField(-23)
sage: OK = K.ring_of_integers()
sage: C = OK.class_group()
sage: P2a, P2b = [P for P, e in (2*K).factor()]
sage: c = C(P2a); c
Fractional ideal class (2, 1/2*w - 1/2)
sage: c.ideal()
Fractional ideal (2, 1/2*w - 1/2)
>>> from sage.all import *
>>> K = QuadraticField(-Integer(23), names=('w',)); (w,) = K._first_ngens(1)
>>> OK = K.ring_of_integers()
>>> C = OK.class_group()
>>> P2a, P2b = [P for P, e in (Integer(2)*K).factor()]
>>> c = C(P2a); c
Fractional ideal class (2, 1/2*w - 1/2)
>>> c.ideal()
Fractional ideal (2, 1/2*w - 1/2)
inverse()[source]

Return the multiplicative inverse of this ideal class.

EXAMPLES:

sage: x = polygen(ZZ, 'x')
sage: K.<a> = NumberField(x^3 - 3*x + 8); G = K.class_group()
sage: G(2, a).inverse()
Fractional ideal class (2, a^2 + 2*a - 1)
sage: ~G(2, a)
Fractional ideal class (2, a^2 + 2*a - 1)
>>> from sage.all import *
>>> x = polygen(ZZ, 'x')
>>> K = NumberField(x**Integer(3) - Integer(3)*x + Integer(8), names=('a',)); (a,) = K._first_ngens(1); G = K.class_group()
>>> G(Integer(2), a).inverse()
Fractional ideal class (2, a^2 + 2*a - 1)
>>> ~G(Integer(2), a)
Fractional ideal class (2, a^2 + 2*a - 1)
is_principal()[source]

Return True iff this ideal class is the trivial (principal) class.

EXAMPLES:

sage: K.<w> = QuadraticField(-23)
sage: OK = K.ring_of_integers()
sage: C = OK.class_group()
sage: P2a, P2b = [P for P, e in (2*K).factor()]
sage: c = C(P2a)
sage: c.is_principal()
False
sage: (c^2).is_principal()
False
sage: (c^3).is_principal()
True
>>> from sage.all import *
>>> K = QuadraticField(-Integer(23), names=('w',)); (w,) = K._first_ngens(1)
>>> OK = K.ring_of_integers()
>>> C = OK.class_group()
>>> P2a, P2b = [P for P, e in (Integer(2)*K).factor()]
>>> c = C(P2a)
>>> c.is_principal()
False
>>> (c**Integer(2)).is_principal()
False
>>> (c**Integer(3)).is_principal()
True
reduce()[source]

Return representative for this ideal class that has been reduced using PARI’s pari:idealred.

EXAMPLES:

sage: x = polygen(ZZ, 'x')
sage: k.<a> = NumberField(x^2 + 20072); G = k.class_group(); G
Class group of order 76 with structure C38 x C2 of
 Number Field in a with defining polynomial x^2 + 20072
sage: I = (G.0)^11; I
Fractional ideal class (33, 1/2*a + 8)
sage: J = G(I.ideal()^5); J
Fractional ideal class (39135393, 1/2*a + 13654253)
sage: J.reduce()
Fractional ideal class (73, 1/2*a + 47)
sage: J == I^5
True
>>> from sage.all import *
>>> x = polygen(ZZ, 'x')
>>> k = NumberField(x**Integer(2) + Integer(20072), names=('a',)); (a,) = k._first_ngens(1); G = k.class_group(); G
Class group of order 76 with structure C38 x C2 of
 Number Field in a with defining polynomial x^2 + 20072
>>> I = (G.gen(0))**Integer(11); I
Fractional ideal class (33, 1/2*a + 8)
>>> J = G(I.ideal()**Integer(5)); J
Fractional ideal class (39135393, 1/2*a + 13654253)
>>> J.reduce()
Fractional ideal class (73, 1/2*a + 47)
>>> J == I**Integer(5)
True
representative_prime(norm_bound=1000)[source]

Return a prime ideal in this ideal class.

INPUT:

  • norm_bound – (positive integer) upper bound on the norm of primes tested

EXAMPLES:

sage: x = polygen(ZZ, 'x')
sage: K.<a> = NumberField(x^2 + 31)
sage: K.class_number()
3
sage: Cl = K.class_group()
sage: [c.representative_prime() for c in Cl]
[Fractional ideal (3),
 Fractional ideal (2, 1/2*a + 1/2),
 Fractional ideal (2, 1/2*a - 1/2)]

sage: K.<a> = NumberField(x^2 + 223)
sage: K.class_number()
7
sage: Cl = K.class_group()
sage: [c.representative_prime() for c in Cl]
[Fractional ideal (3),
 Fractional ideal (2, 1/2*a + 1/2),
 Fractional ideal (17, 1/2*a + 7/2),
 Fractional ideal (7, 1/2*a - 1/2),
 Fractional ideal (7, 1/2*a + 1/2),
 Fractional ideal (17, 1/2*a + 27/2),
 Fractional ideal (2, 1/2*a - 1/2)]
>>> from sage.all import *
>>> x = polygen(ZZ, 'x')
>>> K = NumberField(x**Integer(2) + Integer(31), names=('a',)); (a,) = K._first_ngens(1)
>>> K.class_number()
3
>>> Cl = K.class_group()
>>> [c.representative_prime() for c in Cl]
[Fractional ideal (3),
 Fractional ideal (2, 1/2*a + 1/2),
 Fractional ideal (2, 1/2*a - 1/2)]

>>> K = NumberField(x**Integer(2) + Integer(223), names=('a',)); (a,) = K._first_ngens(1)
>>> K.class_number()
7
>>> Cl = K.class_group()
>>> [c.representative_prime() for c in Cl]
[Fractional ideal (3),
 Fractional ideal (2, 1/2*a + 1/2),
 Fractional ideal (17, 1/2*a + 7/2),
 Fractional ideal (7, 1/2*a - 1/2),
 Fractional ideal (7, 1/2*a + 1/2),
 Fractional ideal (17, 1/2*a + 27/2),
 Fractional ideal (2, 1/2*a - 1/2)]
class sage.rings.number_field.class_group.SClassGroup(gens_orders, names, number_field, gens, S, proof=True)[source]

Bases: ClassGroup

The \(S\)-class group of a number field.

EXAMPLES:

sage: K.<a> = QuadraticField(-14)
sage: S = K.primes_above(2)
sage: K.S_class_group(S).gens()   # random gens (platform dependent)
(Fractional S-ideal class (3, a + 2),)

sage: K.<a> = QuadraticField(-974)
sage: CS = K.S_class_group(K.primes_above(2)); CS
S-class group of order 18 with structure C6 x C3 of
 Number Field in a with defining polynomial x^2 + 974 with a = 31.20897306865447?*I
sage: CS.gen(0) # random
Fractional S-ideal class (3, a + 2)
sage: CS.gen(1) # random
Fractional S-ideal class (31, a + 24)
>>> from sage.all import *
>>> K = QuadraticField(-Integer(14), names=('a',)); (a,) = K._first_ngens(1)
>>> S = K.primes_above(Integer(2))
>>> K.S_class_group(S).gens()   # random gens (platform dependent)
(Fractional S-ideal class (3, a + 2),)

>>> K = QuadraticField(-Integer(974), names=('a',)); (a,) = K._first_ngens(1)
>>> CS = K.S_class_group(K.primes_above(Integer(2))); CS
S-class group of order 18 with structure C6 x C3 of
 Number Field in a with defining polynomial x^2 + 974 with a = 31.20897306865447?*I
>>> CS.gen(Integer(0)) # random
Fractional S-ideal class (3, a + 2)
>>> CS.gen(Integer(1)) # random
Fractional S-ideal class (31, a + 24)
Element[source]

alias of SFractionalIdealClass

S()[source]

Return the set (or rather tuple) of primes used to define this class group.

EXAMPLES:

sage: K.<a> = QuadraticField(-14)
sage: I = K.ideal(2, a)
sage: S = (I,)
sage: CS = K.S_class_group(S);CS
S-class group of order 2 with structure C2 of
 Number Field in a with defining polynomial x^2 + 14 with a = 3.741657386773942?*I
sage: T = tuple()
sage: CT = K.S_class_group(T);CT
S-class group of order 4 with structure C4 of
 Number Field in a with defining polynomial x^2 + 14 with a = 3.741657386773942?*I
sage: CS.S()
(Fractional ideal (2, a),)
sage: CT.S()
()
>>> from sage.all import *
>>> K = QuadraticField(-Integer(14), names=('a',)); (a,) = K._first_ngens(1)
>>> I = K.ideal(Integer(2), a)
>>> S = (I,)
>>> CS = K.S_class_group(S);CS
S-class group of order 2 with structure C2 of
 Number Field in a with defining polynomial x^2 + 14 with a = 3.741657386773942?*I
>>> T = tuple()
>>> CT = K.S_class_group(T);CT
S-class group of order 4 with structure C4 of
 Number Field in a with defining polynomial x^2 + 14 with a = 3.741657386773942?*I
>>> CS.S()
(Fractional ideal (2, a),)
>>> CT.S()
()
class sage.rings.number_field.class_group.SFractionalIdealClass(parent, element, ideal=None)[source]

Bases: FractionalIdealClass

An \(S\)-fractional ideal class in a number field for a tuple \(S\) of primes.

EXAMPLES:

sage: K.<a> = QuadraticField(-14)
sage: I = K.ideal(2, a)
sage: S = (I,)
sage: CS = K.S_class_group(S)
sage: J = K.ideal(7, a)
sage: G = K.ideal(3, a + 1)
sage: CS(I)
Trivial S-ideal class
sage: CS(J)
Trivial S-ideal class
sage: CS(G)
Fractional S-ideal class (3, a + 1)
>>> from sage.all import *
>>> K = QuadraticField(-Integer(14), names=('a',)); (a,) = K._first_ngens(1)
>>> I = K.ideal(Integer(2), a)
>>> S = (I,)
>>> CS = K.S_class_group(S)
>>> J = K.ideal(Integer(7), a)
>>> G = K.ideal(Integer(3), a + Integer(1))
>>> CS(I)
Trivial S-ideal class
>>> CS(J)
Trivial S-ideal class
>>> CS(G)
Fractional S-ideal class (3, a + 1)

sage: K.<a> = QuadraticField(-14)
sage: I = K.ideal(2, a)
sage: S = (I,)
sage: CS = K.S_class_group(S)
sage: J = K.ideal(7, a)
sage: G = K.ideal(3, a + 1)
sage: CS(I).ideal()
Fractional ideal (2, a)
sage: CS(J).ideal()
Fractional ideal (7, a)
sage: CS(G).ideal()
Fractional ideal (3, a + 1)
>>> from sage.all import *
>>> K = QuadraticField(-Integer(14), names=('a',)); (a,) = K._first_ngens(1)
>>> I = K.ideal(Integer(2), a)
>>> S = (I,)
>>> CS = K.S_class_group(S)
>>> J = K.ideal(Integer(7), a)
>>> G = K.ideal(Integer(3), a + Integer(1))
>>> CS(I).ideal()
Fractional ideal (2, a)
>>> CS(J).ideal()
Fractional ideal (7, a)
>>> CS(G).ideal()
Fractional ideal (3, a + 1)

sage: K.<a> = QuadraticField(-14)
sage: I = K.ideal(2, a)
sage: S = (I,)
sage: CS = K.S_class_group(S)
sage: G = K.ideal(3, a + 1)
sage: CS(G).inverse()
Fractional S-ideal class (3, a + 2)
>>> from sage.all import *
>>> K = QuadraticField(-Integer(14), names=('a',)); (a,) = K._first_ngens(1)
>>> I = K.ideal(Integer(2), a)
>>> S = (I,)
>>> CS = K.S_class_group(S)
>>> G = K.ideal(Integer(3), a + Integer(1))
>>> CS(G).inverse()
Fractional S-ideal class (3, a + 2)