@@ -2120,6 +2120,84 @@ cdef class FiniteField(Field):
2120
2120
python_int = int .from_bytes(input_bytes, byteorder = byteorder)
2121
2121
return self .from_integer(python_int)
2122
2122
2123
+ def _roots_univariate_polynomial (self , f , ring , multiplicities , **kwargs ):
2124
+ r """
2125
+ Return the roots of the univariate polynomial ``f``.
2126
+
2127
+ INPUT:
2128
+
2129
+ - ``f`` - a polynomial defined over this field
2130
+
2131
+ - ``ring`` - the ring to find roots in.
2132
+
2133
+ - ``multiplicities`` - bool ( default: ``True``) . If ``True``, return
2134
+ list of pairs `( r, n) `, where `r` is a root and `n` is its
2135
+ multiplicity. If ``False``, just return the unique roots, with no
2136
+ information about multiplicities.
2137
+
2138
+ - ``kwargs`` - ignored
2139
+
2140
+ TESTS::
2141
+ We can take the roots of a polynomial defined over a finite field
2142
+ sage: set_random_seed( 31337)
2143
+ sage: p = random_prime( 2^ 128)
2144
+ sage: R. <x> = Zmod( p) []
2145
+ sage: f = R. random_element( degree=15)
2146
+ sage: f. roots( )
2147
+ [(117558869610275297997958296126212805270, 1) ]
2148
+
2149
+ We can take the roots of a polynomial defined over a finite field without multiplicities
2150
+ sage: set_random_seed( 31337)
2151
+ sage: p = random_prime( 2^ 128)
2152
+ sage: R. <x> = Zmod( p) []
2153
+ sage: f = R. random_element( degree=150)
2154
+ sage: f. roots( multiplicities=False)
2155
+ [116560079209701720510648792531840294827 ]
2156
+
2157
+ We can take the roots of a polynomial defined over a finite field extension
2158
+ sage: set_random_seed( 31337)
2159
+ sage: F. <a> = GF(( 2, 10))
2160
+ sage: R. <x> = F[]
2161
+ sage: f = R. random_element( degree=10)
2162
+ sage: f. roots( )
2163
+ [(a^9 + a^8 + a^6 + a^4 + a^2, 1) ]
2164
+ sage: f. roots( multiplicities=False)
2165
+ [a^9 + a^8 + a^6 + a^4 + a^2 ]
2166
+
2167
+ We can take the roots of a high degree polynomial in a reasonable time
2168
+ sage: set_random_seed( 31337)
2169
+ sage: p = random_prime( 2^ 128)
2170
+ sage: F = GF( p)
2171
+ sage: R. <x> = F[]
2172
+ sage: f = R. random_element( degree=10000)
2173
+ sage: f. roots( multiplicities=False)
2174
+ [65940671326230628578511607550463701471 ]
2175
+ """
2176
+
2177
+ K = f.base_ring()
2178
+ L = K if ring is None else ring
2179
+
2180
+ if K != L:
2181
+ try :
2182
+ f_L = f.change_ring(L)
2183
+ except (TypeError , ValueError ):
2184
+ if L.is_exact() and L.is_subring(K):
2185
+ return f._roots_in_subring(L, multiplicities)
2186
+ else :
2187
+ raise
2188
+ return f_L.roots(multiplicities = multiplicities)
2189
+
2190
+ if multiplicities:
2191
+ return f._roots_from_factorization(f.factor(), multiplicities)
2192
+ else :
2193
+ R = f.parent()
2194
+ x = R.gen()
2195
+ p = K.order()
2196
+ g = pow (x, p, f) - x
2197
+ g = f.gcd(g)
2198
+ return g._roots_from_factorization(g.factor(), False )
2199
+
2200
+
2123
2201
2124
2202
def unpickle_FiniteField_ext (_type , order , variable_name , modulus , kwargs ):
2125
2203
r """
0 commit comments