Array Classes¶
The galois
library subclasses ndarray
to provide arithmetic over Galois fields and rings (future).
Array
subclasses¶
The main abstract base class is Array
. It has two abstract subclasses: FieldArray
and
RingArray
(future). None of these abstract classes may be instantiated directly. Instead, specific
subclasses for GF()
and GR()
(future).
FieldArray
subclasses¶
A FieldArray
subclass is created using the class factory function GF()
.
In [1]: GF = galois.GF(3**5)
In [2]: print(GF.properties)
Galois Field:
name: GF(3^5)
characteristic: 3
degree: 5
order: 243
irreducible_poly: x^5 + 2x + 1
is_primitive_poly: True
primitive_element: x
In [3]: GF = galois.GF(3**5, repr="poly")
In [4]: print(GF.properties)
Galois Field:
name: GF(3^5)
characteristic: 3
degree: 5
order: 243
irreducible_poly: x^5 + 2x + 1
is_primitive_poly: True
primitive_element: x
In [5]: GF = galois.GF(3**5, repr="power")
In [6]: print(GF.properties)
Galois Field:
name: GF(3^5)
characteristic: 3
degree: 5
order: 243
irreducible_poly: x^5 + 2x + 1
is_primitive_poly: True
primitive_element: x
Speed up creation of large finite field classes
For very large finite fields, the FieldArray
subclass creation time can be reduced by explicitly specifying
In [7]: GF = galois.GF(2, 100)
In [8]: print(GF.properties)
Galois Field:
name: GF(2^100)
characteristic: 2
degree: 100
order: 1267650600228229401496703205376
irreducible_poly: x^100 + x^57 + x^56 + x^55 + x^52 + x^48 + x^47 + x^46 + x^45 + x^44 + x^43 + x^41 + x^37 + x^36 + x^35 + x^34 + x^31 + x^30 + x^27 + x^25 + x^24 + x^22 + x^20 + x^19 + x^16 + x^15 + x^11 + x^9 + x^8 + x^6 + x^5 + x^3 + 1
is_primitive_poly: True
primitive_element: x
Furthermore, if you already know the desired irreducible polynomial is irreducible and the primitive element is a generator of
the multiplicative group, you can specify verify=False
to skip the verification step. This eliminates the need to factor
In [9]: GF = galois.GF(109987, 4, irreducible_poly="x^4 + 3x^2 + 100525x + 3", primitive_element="x", verify=False)
In [10]: print(GF.properties)
Galois Field:
name: GF(109987^4)
characteristic: 109987
degree: 4
order: 146340800268433348561
irreducible_poly: x^4 + 3x^2 + 100525x + 3
is_primitive_poly: True
primitive_element: x
The GF
class is a subclass of FieldArray
and a subclasses of ndarray
.
In [11]: issubclass(GF, galois.FieldArray)
Out[11]: True
In [12]: issubclass(GF, galois.Array)
Out[12]: True
In [13]: issubclass(GF, np.ndarray)
Out[13]: True
Class singletons¶
FieldArray
subclasses of the same type (order, irreducible polynomial, and primitive element) are singletons.
Here is the creation (twice) of the field
In [14]: galois.GF(3**5) is galois.GF(3**5)
Out[14]: True
The expense of class creation is incurred only once. So, subsequent calls of galois.GF(3**5)
are extremely inexpensive.
However, the field GF()
returns a unique FieldArray
subclass.
In [15]: galois.GF(3**5) is galois.GF(3**5, irreducible_poly="x^5 + x^2 + x + 2")
Out[15]: False
Methods and properties¶
All of the methods and properties related to FieldArray
. For example, the irreducible polynomial of the finite field is accessed
with irreducible_poly
.
In [16]: GF.irreducible_poly
Out[16]: Poly(x^5 + 2x + 1, GF(3))
FieldArray
instances¶
A FieldArray
instance is created using GF
’s constructor.
In [17]: x = GF([23, 78, 163, 124])
In [18]: x
Out[18]: GF([ 23, 78, 163, 124], order=3^5)
In [19]: x = GF([23, 78, 163, 124])
In [20]: x
Out[20]:
GF([ 2α^2 + α + 2, 2α^3 + 2α^2 + 2α,
2α^4 + 1, α^4 + α^3 + α^2 + 2α + 1], order=3^5)
In [21]: x = GF([23, 78, 163, 124])
In [22]: x
Out[22]: GF([ α^17, α^132, α^241, α^41], order=3^5)
The array x
is an instance of FieldArray
and also an instance of ndarray
.
In [23]: isinstance(x, GF)
Out[23]: True
In [24]: isinstance(x, galois.FieldArray)
Out[24]: True
In [25]: isinstance(x, galois.Array)
Out[25]: True
In [26]: isinstance(x, np.ndarray)
Out[26]: True
The FieldArray
subclass is easily recovered from a FieldArray
instance using type()
.
In [27]: type(x) is GF
Out[27]: True
Constructors¶
Several classmethods are defined in FieldArray
that function as alternate constructors. By convention,
alternate constructors use PascalCase
while other classmethods use snake_case
.
For example, to generate a random array of given shape call Random()
.
In [28]: GF.Random((3, 2), seed=1)
Out[28]:
GF([[242, 216],
[ 32, 114],
[230, 179]], order=3^5)
In [29]: GF.Random((3, 2), seed=1)
Out[29]:
GF([[2α^4 + 2α^3 + 2α^2 + 2α + 2, 2α^4 + 2α^3],
[ α^3 + α + 2, α^4 + α^3 + 2α],
[ 2α^4 + 2α^3 + α^2 + α + 2, 2α^4 + α^2 + 2α + 2]], order=3^5)
In [30]: GF.Random((3, 2), seed=1)
Out[30]:
GF([[α^185, α^193],
[ α^49, α^231],
[ α^81, α^60]], order=3^5)
Or, create an identity matrix using Identity()
.
In [31]: GF.Identity(4)
Out[31]:
GF([[1, 0, 0, 0],
[0, 1, 0, 0],
[0, 0, 1, 0],
[0, 0, 0, 1]], order=3^5)
In [32]: GF.Identity(4)
Out[32]:
GF([[1, 0, 0, 0],
[0, 1, 0, 0],
[0, 0, 1, 0],
[0, 0, 0, 1]], order=3^5)
In [33]: GF.Identity(4)
Out[33]:
GF([[1, 0, 0, 0],
[0, 1, 0, 0],
[0, 0, 1, 0],
[0, 0, 0, 1]], order=3^5)
Methods¶
All of the methods that act on FieldArray
instances are documented as instance methods in FieldArray
.
For example, the multiplicative order of each finite field element is calculated using multiplicative_order()
.
In [34]: x.multiplicative_order()
Out[34]: array([242, 11, 242, 242])