Macaulay2 Engine
Loading...
Searching...
No Matches
aring-gf-flint-big.cpp
Go to the documentation of this file.
1// Copyright 2014 Michael E. Stillman
2
4#include "relem.hpp"
5#include "poly.hpp"
6#include "ringmap.hpp"
7
8namespace M2 {
9
11 : mOriginalRing(R),
14{
15
16 // TODO: assert that the base ring of R is ZZ/p.
17 // TODO: if mDimension <= 1 then give an error.
18 ring_elem b = R.copy(a);
20 ring_elem minpoly = mOriginalRing.quotient_element(0);
21
22 std::vector<long> poly;
23 RingElement F(&R, minpoly);
25
26 // warning: flint expects unsigned longs, so we must make
27 // all of these coeffs non-negative.
28 for (long i = poly.size() - 1; i >= 0; i--)
29 {
30 long a = poly[i];
31 if (a == 0) continue;
32 if (a < 0) poly[i] += characteristic();
33 }
34
35 mDimension = poly.size() - 1;
36
37#if 0
38 printf("minpoly: ");
39 for (long i=0; i<poly.size(); i++)
40 printf(" %ld", poly[i]);
41 printf("\n");
42#endif
43 nmod_poly_t mMinPoly;
44 nmod_poly_init(mMinPoly, R.characteristic());
45
46 for (long i = poly.size() - 1; i >= 0; i--)
47 if (poly[i] != 0) nmod_poly_set_coeff_ui(mMinPoly, i, poly[i]);
48
49 fq_nmod_ctx_init_modulus(mContext, mMinPoly, "a");
50#if 0
51 fq_nmod_ctx_print(mContext);
52#endif
53 nmod_poly_clear(mMinPoly);
54
55 // powers of p, as ulongs's
56 mPPowers = newarray_atomic(unsigned int, mDimension + 1);
57 mPPowers[0] = 1;
58 for (long i = 1; i <= mDimension; i++)
59 mPPowers[i] = mPPowers[i - 1] * static_cast<unsigned int>(mCharacteristic);
60
62}
63
73
75 std::vector<long>& poly) const
76{
77 long deg = nmod_poly_degree(&a);
78 poly.resize(deg + 1);
79 for (long i = deg; i >= 0; i--) poly[i] = nmod_poly_get_coeff_ui(&a, i);
80}
81
84 const std::vector<long>& poly) const
85{
86#if 0
87 printf("input = ");
88 for (long i=0; i<poly.size(); i++)
89 printf("%ld ", poly[i]);
90 printf("\n");
91#endif
92 for (long i = poly.size() - 1; i >= 0; i--)
93 {
94 long a = poly[i];
95 if (a == 0) continue;
96 if (a < 0) a += characteristic();
97 nmod_poly_set_coeff_ui(&result, i, a);
98 }
99#if 0
100 printf(" result before reduction = ");
101 fq_nmod_print_pretty(&result, mContext);
102 printf("\n");
103#endif
104 fq_nmod_reduce(&result, mContext);
105#if 0
106 printf(" result = ");
107 fq_nmod_print_pretty(&result, mContext);
108 printf("\n");
109#endif
110}
111
113{
114 if (not mGeneratorComputed)
115 {
116 fq_nmod_init(&mCachedGenerator, mContext);
117 fq_nmod_gen(&mCachedGenerator, mContext);
118 mGeneratorComputed = true;
119 }
120 copy(result_gen, mCachedGenerator);
121}
122
124 const ring_elem f,
125 ElementType& result) const
126{
127 if (&originalRing() != Rf) return false;
128 std::vector<long> poly;
129 RingElement F(Rf, f);
132 return true;
133}
134
136 const ElementType& f) const
137{
138 std::vector<long> poly;
140 result =
142}
143
145 const ElementType& f,
146 ring_elem& result) const
147{
148 // Rg = ZZ/p[x]/F(x) ---> GF(p,n)
149 if (&originalRing() != Rg) return false;
151 return true;
152}
153
155 const ElementType& f,
156 int first_var,
157 ring_elem& result) const
158{
159 const Ring* R = map->get_ring(); // the target ring
160 result = R->from_long(0);
161 if (is_zero(f)) return;
162
163 ring_elem a = map->elem(first_var);
164 std::vector<long> poly;
166 for (long i = poly.size() - 1; i >= 0; i--)
167 {
168 if (!R->is_zero(result)) result = R->mult(a, result);
169 if (poly[i] != 0)
170 {
171 ring_elem c = R->from_long(poly[i]);
172 result = R->add(result, c);
173 }
174 }
175}
176
178{
179 o << "GF(" << characteristic() << "^" << dimension() << ",FlintBig)";
180}
181
183 const ElementType& a,
184 bool p_one,
185 bool p_plus,
186 bool p_parens) const
187{
188 if (is_zero(a))
189 {
190 o << "0";
191 return;
192 }
193 ring_elem b;
194 lift(&originalRing(), a, b);
195 originalRing().elem_text_out(o, b, p_one, p_plus, p_parens);
196}
197
199 const ElementType& g) const
200{
201 long degF = nmod_poly_degree(&f);
202 long degG = nmod_poly_degree(&g);
203 if (degF > degG)
204 return GT;
205 else if (degF < degG)
206 return LT;
207 // now degF == degG
208 for (long i = degF; i >= 0; i--)
209 {
210 long coeffF = nmod_poly_get_coeff_ui(&f, i);
211 long coeffG = nmod_poly_get_coeff_ui(&g, i);
212 if (coeffF > coeffG) return GT;
213 if (coeffG > coeffF) return LT;
214 }
215 return EQ;
216}
217};
218
219// Local Variables:
220// compile-command: "make -C $M2BUILDDIR/Macaulay2/e "
221// indent-tabs-mode: nil
222// End:
M2::ARingGFFlintBig — arbitrary-degree GF(p^k) via FLINT fq_nmod.
#define FLINT_RAND_INIT(x)
Definition aring.hpp:59
#define FLINT_RAND_CLEAR(x)
Definition aring.hpp:60
const PolynomialRing & originalRing() const
void fromSmallIntegerCoefficients(ElementType &result, const std::vector< long > &poly) const
void getGenerator(ElementType &result_gen) const
const PolynomialRing & mOriginalRing
bool lift(const Ring *Rg, const ElementType &f, ring_elem &result) const
const RingElement * mPrimitiveElement
void lift_to_original_ring(ring_elem &result, const ElementType &f) const
bool is_zero(const ElementType &f) const
ARingGFFlintBig(const PolynomialRing &R, const ring_elem a)
bool promote(const Ring *Rf, const ring_elem f, ElementType &result) const
void text_out(buffer &o) const
void elem_text_out(buffer &o, const ElementType &a, bool p_one=true, bool p_plus=false, bool p_parens=false) const
void getSmallIntegerCoefficients(const ElementType &a, std::vector< long > &poly) const
int compare_elems(const ElementType &f, const ElementType &g) const
void eval(const RingMap *map, const ElementType &f, int first_var, ring_elem &result) const
void copy(ElementType &result, const ElementType &a) const
ring_elem fromSmallIntegerCoefficients(const std::vector< long > &coeffs, int var) const
Definition poly.cpp:2249
virtual const PolyRing * getNumeratorRing() const
Definition polyring.hpp:259
Abstract base for the engine's polynomial-ring hierarchy.
Definition polyring.hpp:96
virtual ring_elem add(const ring_elem f, const ring_elem g) const =0
virtual ring_elem from_long(long n) const =0
virtual void elem_text_out(buffer &o, const ring_elem f, bool p_one=true, bool p_plus=false, bool p_parens=false) const =0
long characteristic() const
Definition ring.hpp:159
virtual ring_elem copy(const ring_elem f) const =0
virtual bool is_zero(const ring_elem f) const =0
virtual ring_elem mult(const ring_elem f, const ring_elem g) const =0
static RingElement * make_raw(const Ring *R, ring_elem f)
Definition relem.cpp:20
bool getSmallIntegerCoefficients(std::vector< long > &result_coeffs) const
Definition relem.cpp:421
Front-end-visible "ring element" value: an engine ring_elem paired with the Ring* that gives it meani...
Definition relem.hpp:67
xxx xxx xxx
Definition ring.hpp:102
const ring_elem elem(int i) const
Definition ringmap.hpp:114
const Ring * get_ring() const
Definition ringmap.hpp:111
Engine-side ring homomorphism: stores, for each source-ring variable, the target-ring element it maps...
Definition ringmap.hpp:60
void freemem(void *s)
Definition m2-mem.cpp:103
VALGRIND_MAKE_MEM_DEFINED & result(result)
Definition aring-CC.cpp:3
#define newarray_atomic(T, len)
Definition newdelete.hpp:91
Concrete commutative PolyRing — standard polynomial ring inheriting from PolyRingFlat.
RingElement — tagged (Ring*, ring_elem) pair, the engine's universal element type.
RingMap — engine representation of a ring homomorphism.
const int EQ
Definition style.hpp:40
const int GT
Definition style.hpp:41
const int LT
Definition style.hpp:39