Macaulay2 Engine
Loading...
Searching...
No Matches
aring-zz-gmp.hpp
Go to the documentation of this file.
1// Copyright 2013 Michael E. Stillman
2
3#ifndef _aring_zz_gmp_hpp_
4#define _aring_zz_gmp_hpp_
5
41
42#include "interface/gmp-util.h" // for mpz_reallocate_limbs
43#include "interface/random.h" // for rawRandomInteger
44
45#include "aring.hpp"
46#include "buffer.hpp"
47#include "ringelem.hpp"
48#include "exceptions.hpp"
49#include "ZZ.hpp"
50
51namespace M2 {
57
58class ARingZZGMP : public SimpleARing<ARingZZGMP>
59{
60 public:
61 static const RingID ringID = ring_ZZ;
62
63 typedef __mpz_struct ElementType;
65
66 ARingZZGMP();
68
69 public:
70 // ring informational
71 size_t characteristic() const { return 0; }
72 size_t cardinality() const { return static_cast<size_t>(-1); }
73 unsigned int computeHashValue(const elem& a) const
74 {
75 return static_cast<unsigned int>(mpz_get_ui(&a));
76 }
77
81
82 bool is_unit(const ElementType& f) const
83 {
84 return mpz_cmp_si(&f, 1) == 0 or mpz_cmp_si(&f, -1) == 0;
85 }
86 bool is_zero(const ElementType& f) const { return mpz_sgn(&f) == 0; }
88
91
92 bool is_equal(const ElementType& f, const ElementType& g) const
93 {
94 return mpz_cmp(&f, &g) == 0;
95 }
96 int compare_elems(const ElementType& f, const ElementType& g) const
97 {
98 int cmp = mpz_cmp(&f, &g);
99 if (cmp > 0) return 1;
100 if (cmp < 0) return -1;
101 return 0;
102 }
103
104
107
108 void init_set(ElementType& result, const ElementType& a) const
109 {
110 mpz_init_set(&result, &a);
111 }
112
113 void init(ElementType& result) const { mpz_init(&result); }
114 static void clear(ElementType& result) { mpz_clear(&result); }
115
116 void set(ElementType& result, const ElementType& a) const
117 {
118 mpz_set(&result, &a);
119 }
120
121 void set_zero(ElementType& result) const { mpz_set_si(&result, 0); }
122 void set_from_long(ElementType& result, long a) const
123 {
124 mpz_set_si(&result, a);
125 }
126
127 void set_from_mpz(ElementType& result, mpz_srcptr a) const
128 {
129 // printf("ARingZZ::calling set_from_mpz\n");
130 mpz_set(&result, a);
131 }
132
133 bool set_from_mpq(ElementType& result, mpq_srcptr a) const
134 {
135 if (mpz_cmp_si(mpq_denref(a), 1) == 0)
136 {
137 set_from_mpz(result, mpq_numref(a));
138 return true;
139 }
140 return false;
141 }
142
144 {
145 (void) result;
146 (void) a;
147 return false;
148 }
149
150 void set_var(ElementType& result, int v) const
151 {
152 (void) v;
153 mpz_set_si(&result, 1);
154 }
155
157
160 void negate(ElementType& result, const ElementType& a) const
161 {
162 mpz_neg(&result, &a);
163 }
164
165 void invert(ElementType& result, const ElementType& a) const
166 {
167 if (is_unit(a))
168 set(result, a);
169 else
171 }
172
174 const ElementType& a,
175 const ElementType& b) const
176 {
177 mpz_add(&result, &a, &b);
178 }
179
181 const ElementType& a,
182 const ElementType& b) const
183 {
184 mpz_sub(&result, &a, &b);
185 }
186
188 const ElementType& a,
189 const ElementType& b) const
190 {
191 mpz_submul(&result, &a, &b);
192 }
193
195 const ElementType& a,
196 const ElementType& b) const
197 {
198 mpz_mul(&result, &a, &b);
199 }
200
202
204 const ElementType& a,
205 const ElementType& b) const
206 {
207 if (mpz_divisible_p(&a, &b))
208 {
209 mpz_divexact(&result, &a, &b);
210 }
211 else
212 {
213 throw exc::engine_error("division not exact");
214 }
215 }
216
217 void power(ElementType& result, const ElementType& a, unsigned long n) const
218 {
219 return mpz_pow_ui(&result, &a, n);
220 }
221
223 const ElementType& a,
224 mpz_srcptr n) const
225 {
226 if (mpz_sgn(n) < 0) throw exc::engine_error("can only raise to a nonnegative power");
227 std::pair<bool, int> n1 = RingZZ::get_si(n);
228 if (n1.first)
229 mpz_pow_ui(&result, &a, n1.second);
230 else
231 throw exc::engine_error("exponent too large");
232 }
233
234 void syzygy(const ElementType& a,
235 const ElementType& b,
236 ElementType& x,
237 ElementType& y) const;
239
242 void swap(ElementType& a, ElementType& b) const { mpz_swap(&a, &b); }
244 {
245 rawSetRandomInteger(&result, nullptr);
246 }
247
248
252 void text_out(buffer& o) const { o << "ZZFlint"; }
253 void elem_text_out(buffer& o,
254 const ElementType& a,
255 bool p_one = true,
256 bool p_plus = false,
257 bool p_parens = false) const;
259
262
264 {
265 mpz_ptr b = getmemstructtype(mpz_ptr);
266 mpz_init(b);
267 mpz_set(b, &a);
269 result = ring_elem(b);
270 }
271
273 {
274 const ElementType* t = a.get_mpz();
275 mpz_set(&result, t);
276 }
277
279 {
280 return *a.get_mpz();
281 }
282
284
285 bool promote(const Ring* Rf, const ring_elem f, ElementType& result) const
286 {
287 (void) Rf;
288 (void) f;
289 (void) result;
290 return false;
291 }
292
293 bool lift(const Ring* Rg, const ElementType& f, ring_elem& result) const
294 {
295 (void) Rg;
296 (void) f;
297 (void) result;
298 return false;
299 }
300
301 // map : this --> target(map)
302 // primelem --> map->elem(first_var)
303 // evaluate map(f)
304 void eval(const RingMap* map,
305 const ElementType& f,
306 int first_var,
307 ring_elem& result) const;
308
309 bool coerceToLongInteger(long& result, const ElementType& n) const
310 {
311 result = mpz_get_si(&n);
312 return mpz_fits_slong_p(&n);
313 }
314};
315};
316
317#endif
318
319// Local Variables:
320// compile-command: "make -C $M2BUILDDIR/Macaulay2/e "
321// indent-tabs-mode: nil
322// End:
Legacy RingZZ — a Ring-derived integer ring backed by GMP mpz_t.
Shared base of the aring framework (namespace M2) that unifies the engine's coefficient rings.
Append-only GC-backed byte buffer used throughout the engine for text output.
void subtract(ElementType &result, const ElementType &a, const ElementType &b) const
static const RingID ringID
void to_ring_elem(ring_elem &result, const ElementType &a) const
void subtract_multiple(ElementType &result, const ElementType &a, const ElementType &b) const
void set_from_mpz(ElementType &result, mpz_srcptr a) const
void mult(ElementType &result, const ElementType &a, const ElementType &b) const
void init(ElementType &result) const
void invert(ElementType &result, const ElementType &a) const
void text_out(buffer &o) const
bool is_unit(const ElementType &f) const
int compare_elems(const ElementType &f, const ElementType &g) const
size_t characteristic() const
bool set_from_mpq(ElementType &result, mpq_srcptr a) const
bool set_from_BigReal(ElementType &result, gmp_RR a) const
void eval(const RingMap *map, const ElementType &f, int first_var, ring_elem &result) const
bool lift(const Ring *Rg, const ElementType &f, ring_elem &result) const
void set_var(ElementType &result, int v) const
bool promote(const Ring *Rf, const ring_elem f, ElementType &result) const
ElementType elem
void syzygy(const ElementType &a, const ElementType &b, ElementType &x, ElementType &y) const
void init_set(ElementType &result, const ElementType &a) const
void add(ElementType &result, const ElementType &a, const ElementType &b) const
static void clear(ElementType &result)
void power_mpz(ElementType &result, const ElementType &a, mpz_srcptr n) const
void power(ElementType &result, const ElementType &a, unsigned long n) const
void from_ring_elem(ElementType &result, const ring_elem &a) const
void set(ElementType &result, const ElementType &a) const
void set_zero(ElementType &result) const
void random(ElementType &result) const
__mpz_struct ElementType
size_t cardinality() const
void elem_text_out(buffer &o, const ElementType &a, bool p_one=true, bool p_plus=false, bool p_parens=false) const
bool coerceToLongInteger(long &result, const ElementType &n) const
const ElementType & from_ring_elem_const(const ring_elem &a) const
void negate(ElementType &result, const ElementType &a) const
void divide(ElementType &result, const ElementType &a, const ElementType &b) const
exact division of integers.
bool is_equal(const ElementType &f, const ElementType &g) const
unsigned int computeHashValue(const elem &a) const
void set_from_long(ElementType &result, long a) const
bool is_zero(const ElementType &f) const
void swap(ElementType &a, ElementType &b) const
A base class for simple ARings.
Definition aring.hpp:147
xxx xxx xxx
Definition ring.hpp:102
Engine-side ring homomorphism: stores, for each source-ring variable, the target-ring element it maps...
Definition ringmap.hpp:60
static std::pair< bool, int > get_si(mpz_srcptr n)
Definition ZZ.cpp:46
namespace exc — internal C++ exception types and the TRY / CATCH macro pair.
void mpz_reallocate_limbs(mpz_ptr _z)
Definition gmp-util.h:46
Inline helpers that move GMP / MPFR / MPFI limbs from malloc-managed storage into the bdwgc heap.
RingID
Definition aring.hpp:75
@ ring_ZZ
Definition aring.hpp:77
VALGRIND_MAKE_MEM_DEFINED & result(result)
#define getmemstructtype(S)
Definition m2-mem.h:143
mpfr_srcptr gmp_RR
Definition m2-types.h:148
Definition aring-CC.cpp:3
volatile int x
void rawSetRandomInteger(mpz_ptr result, gmp_ZZ maxN)
Definition random.cpp:56
Engine-boundary C API for the engine's PRNG and rational / real / complex random draws.
ring_elem — the universal value type carried by every Ring* in the engine.
mpz_srcptr get_mpz() const
Definition ringelem.hpp:127