source: git/libpolys/coeffs/rintegers.cc @ 246bbb

spielwiese
Last change on this file since 246bbb was 16f511, checked in by Oleksandr Motsak <motsak@…>, 11 years ago
Fixed the usage of "config.h" (if defined HAVE_CONFIG_H)
  • Property mode set to 100644
File size: 9.2 KB
Line 
1/****************************************
2*  Computer Algebra System SINGULAR     *
3****************************************/
4/*
5* ABSTRACT: numbers modulo n
6*/
7#ifdef HAVE_CONFIG_H
8#include "config.h"
9#endif /* HAVE_CONFIG_H */
10#include <misc/auxiliary.h>
11
12#ifdef HAVE_RINGS
13
14#include <string.h>
15#include <misc/mylimits.h>
16#include <coeffs/coeffs.h>
17#include <reporter/reporter.h>
18#include <omalloc/omalloc.h>
19#include <coeffs/numbers.h>
20#include <coeffs/longrat.h>
21#include <coeffs/mpr_complex.h>
22#include <coeffs/rintegers.h>
23#include "si_gmp.h"
24
25/// Our Type!
26static const n_coeffType ID = n_Z;
27
28omBin gmp_nrz_bin = omGetSpecBin(sizeof(mpz_t));
29
30/*
31 * Multiply two numbers
32 */
33number nrzMult (number a, number b, const coeffs)
34{
35  int_number erg = (int_number) omAllocBin(gmp_nrz_bin);
36  mpz_init(erg);
37  mpz_mul(erg, (int_number) a, (int_number) b);
38  return (number) erg;
39}
40
41/*
42 * Give the smallest non unit k, such that a * x = k = b * y has a solution
43 */
44number nrzLcm (number a,number b,const coeffs)
45{
46  int_number erg = (int_number) omAllocBin(gmp_nrz_bin);
47  mpz_init(erg);
48  mpz_lcm(erg, (int_number) a, (int_number) b);
49  return (number) erg;
50}
51
52/*
53 * Give the largest non unit k, such that a = x * k, b = y * k has
54 * a solution.
55 */
56number nrzGcd (number a,number b,const coeffs)
57{
58  int_number erg = (int_number) omAllocBin(gmp_nrz_bin);
59  mpz_init(erg);
60  mpz_gcd(erg, (int_number) a, (int_number) b);
61  return (number) erg;
62}
63
64/*
65 * Give the largest non unit k, such that a = x * k, b = y * k has
66 * a solution and r, s, s.t. k = s*a + t*b
67 */
68number  nrzExtGcd (number a, number b, number *s, number *t, const coeffs)
69{
70  int_number erg = (int_number) omAllocBin(gmp_nrz_bin);
71  int_number bs = (int_number) omAllocBin(gmp_nrz_bin);
72  int_number bt = (int_number) omAllocBin(gmp_nrz_bin);
73  mpz_init(erg);
74  mpz_init(bs);
75  mpz_init(bt);
76  mpz_gcdext(erg, bs, bt, (int_number) a, (int_number) b);
77  *s = (number) bs;
78  *t = (number) bt;
79  return (number) erg;
80}
81
82void nrzPower (number a, int i, number * result, const coeffs)
83{
84  int_number erg = (int_number) omAllocBin(gmp_nrz_bin);
85  mpz_init(erg);
86  mpz_pow_ui(erg, (int_number) a, i);
87  *result = (number) erg;
88}
89
90/*
91 * create a number from int
92 */
93number nrzInit (long i, const coeffs)
94{
95  int_number erg = (int_number) omAllocBin(gmp_nrz_bin);
96  mpz_init_set_si(erg, i);
97  return (number) erg;
98}
99
100void nrzDelete(number *a, const coeffs)
101{
102  if (*a == NULL) return;
103  mpz_clear((int_number) *a);
104  omFreeBin((ADDRESS) *a, gmp_nrz_bin);
105  *a = NULL;
106}
107
108number nrzCopy(number a, const coeffs)
109{
110  int_number erg = (int_number) omAllocBin(gmp_nrz_bin);
111  mpz_init_set(erg, (int_number) a);
112  return (number) erg;
113}
114
115#if 0
116number nrzCopyMap(number a, const coeffs /*src*/, const coeffs dst)
117{
118  return nrzCopy(a,dst);
119}
120#endif
121
122int nrzSize(number a, const coeffs)
123{
124  if (a == NULL) return 0;
125  return sizeof(mpz_t);
126}
127
128/*
129 * convert a number to int
130 */
131int nrzInt(number &n, const coeffs)
132{
133  return (int) mpz_get_si( (int_number)n);
134}
135
136number nrzAdd (number a, number b, const coeffs)
137{
138  int_number erg = (int_number) omAllocBin(gmp_nrz_bin);
139  mpz_init(erg);
140  mpz_add(erg, (int_number) a, (int_number) b);
141  return (number) erg;
142}
143
144number nrzSub (number a, number b, const coeffs)
145{
146  int_number erg = (int_number) omAllocBin(gmp_nrz_bin);
147  mpz_init(erg);
148  mpz_sub(erg, (int_number) a, (int_number) b);
149  return (number) erg;
150}
151
152number  nrzGetUnit (number, const coeffs r)
153{
154  return nrzInit(1, r);
155}
156
157BOOLEAN nrzIsUnit (number a, const coeffs)
158{
159  return 0 == mpz_cmpabs_ui((int_number) a, 1);
160}
161
162BOOLEAN nrzIsZero (number  a, const coeffs)
163{
164  return 0 == mpz_cmpabs_ui((int_number) a, 0);
165}
166
167BOOLEAN nrzIsOne (number a, const coeffs)
168{
169  return (a!=NULL) && (0 == mpz_cmp_si((int_number) a, 1));
170}
171
172BOOLEAN nrzIsMOne (number a, const coeffs)
173{
174  return (a!=NULL) && (0 == mpz_cmp_si((int_number) a, -1));
175}
176
177BOOLEAN nrzEqual (number a,number b, const coeffs)
178{
179  return 0 == mpz_cmp((int_number) a, (int_number) b);
180}
181
182BOOLEAN nrzGreater (number a,number b, const coeffs)
183{
184  return 0 < mpz_cmp((int_number) a, (int_number) b);
185}
186
187BOOLEAN nrzGreaterZero (number k, const coeffs)
188{
189  return 0 < mpz_cmp_si((int_number) k, 0);
190}
191
192int nrzDivComp(number a, number b, const coeffs r)
193{
194  if (nrzDivBy(a, b, r))
195  {
196    if (nrzDivBy(b, a, r)) return 2;
197    return -1;
198  }
199  if (nrzDivBy(b, a, r)) return 1;
200  return 0;
201}
202
203BOOLEAN nrzDivBy (number a,number b, const coeffs)
204{
205  return mpz_divisible_p((int_number) a, (int_number) b) != 0;
206}
207
208number nrzDiv (number a,number b, const coeffs R)
209{
210  int_number erg = (int_number) omAllocBin(gmp_nrz_bin);
211  mpz_init(erg);
212  int_number r = (int_number) omAllocBin(gmp_nrz_bin);
213  mpz_init(r);
214  mpz_tdiv_qr(erg, r, (int_number) a, (int_number) b);
215  if (!nrzIsZero((number) r, R))
216  {
217    WerrorS("Division by non divisible element.");
218    WerrorS("Result is without remainder.");
219  }
220  mpz_clear(r);
221  omFreeBin(r, gmp_nrz_bin);
222  return (number) erg;
223}
224
225number nrzIntDiv (number a,number b, const coeffs)
226{
227  int_number erg = (int_number) omAllocBin(gmp_nrz_bin);
228  mpz_init(erg);
229  mpz_tdiv_q(erg, (int_number) a, (int_number) b);
230  return (number) erg;
231}
232
233number nrzIntMod (number a,number b, const coeffs)
234{
235  int_number erg = (int_number) omAllocBin(gmp_nrz_bin);
236  mpz_init(erg);
237  int_number r = (int_number) omAllocBin(gmp_nrz_bin);
238  mpz_init(r);
239  mpz_tdiv_qr(erg, r, (int_number) a, (int_number) b);
240  mpz_clear(erg);
241  return (number) r;
242}
243
244number  nrzInvers (number c, const coeffs r)
245{
246  if (!nrzIsUnit((number) c, r))
247  {
248    WerrorS("Non invertible element.");
249    return (number)0; //TODO
250  }
251  return nrzCopy(c,r);
252}
253
254number nrzNeg (number c, const coeffs)
255{
256// nNeg inplace !!!
257  mpz_mul_si((int_number) c, (int_number) c, -1);
258  return c;
259}
260
261number nrzMapMachineInt(number from, const coeffs /*src*/, const coeffs /*dst*/)
262{
263  int_number erg = (int_number) omAllocBin(gmp_nrz_bin);
264  mpz_init_set_ui(erg, (NATNUMBER) from);
265  return (number) erg;
266}
267
268number nrzMapZp(number from, const coeffs /*src*/, const coeffs /*dst*/)
269{
270  int_number erg = (int_number) omAllocBin(gmp_nrz_bin);
271  mpz_init_set_si(erg, (long) from);
272  return (number) erg;
273}
274
275number nrzMapQ(number from, const coeffs src, const coeffs /*dst*/)
276{
277  int_number erg = (int_number) omAllocBin(gmp_nrz_bin);
278  mpz_init(erg);
279  nlGMP(from, (number) erg, src);
280  return (number) erg;
281}
282
283nMapFunc nrzSetMap(const coeffs src, const coeffs /*dst*/)
284{
285  /* dst = currRing */
286  if (nCoeff_is_Ring_Z(src) || nCoeff_is_Ring_ModN(src) || nCoeff_is_Ring_PtoM(src))
287  {
288    return ndCopyMap; //nrzCopyMap;
289  }
290  if (nCoeff_is_Ring_2toM(src))
291  {
292    return nrzMapMachineInt;
293  }
294  if (nCoeff_is_Zp(src))
295  {
296    return nrzMapZp;
297  }
298  if (nCoeff_is_Q(src))
299  {
300    return nrzMapQ;
301  }
302  return NULL;      // default
303}
304
305
306/*
307 * set the exponent (allocate and init tables) (TODO)
308 */
309
310void nrzSetExp(int, coeffs)
311{
312}
313
314void nrzInitExp(int, coeffs)
315{
316}
317
318#ifdef LDEBUG
319BOOLEAN nrzDBTest (number, const char *, const int, const coeffs)
320{
321  return TRUE;//TODO
322}
323#endif
324
325void nrzWrite (number &a, const coeffs)
326{
327  char *s,*z;
328  if (a==NULL)
329  {
330    StringAppendS("o");
331  }
332  else
333  {
334    int l=mpz_sizeinbase((int_number) a, 10) + 2;
335    s=(char*)omAlloc(l);
336    z=mpz_get_str(s,10,(int_number) a);
337    StringAppendS(z);
338    omFreeSize((ADDRESS)s,l);
339  }
340}
341
342/*2
343* extracts a long integer from s, returns the rest    (COPY FROM longrat0.cc)
344*/
345static const char * nlEatLongC(char *s, mpz_ptr i)
346{
347  const char * start=s;
348
349  if (*s<'0' || *s>'9')
350  {
351    mpz_set_si(i,1);
352    return s;
353  }
354  while (*s >= '0' && *s <= '9') s++;
355  if (*s=='\0')
356  {
357    mpz_set_str(i,start,10);
358  }
359  else
360  {
361    char c=*s;
362    *s='\0';
363    mpz_set_str(i,start,10);
364    *s=c;
365  }
366  return s;
367}
368
369const char * nrzRead (const char *s, number *a, const coeffs)
370{
371  int_number z = (int_number) omAllocBin(gmp_nrz_bin);
372  {
373    mpz_init(z);
374    s = nlEatLongC((char *) s, z);
375  }
376  *a = (number) z;
377  return s;
378}
379
380void    nrzCoeffWrite  (const coeffs, BOOLEAN /*details*/)
381{
382  PrintS("//   coeff. ring is : Integers\n");
383}
384
385
386BOOLEAN nrzInitChar(coeffs r,  void *)
387{
388  assume( getCoeffType(r) == ID );
389  r->nCoeffIsEqual = ndCoeffIsEqual;
390  r->cfKillChar = ndKillChar;
391  r->cfMult  = nrzMult;
392  r->cfSub   = nrzSub;
393  r->cfAdd   = nrzAdd;
394  r->cfDiv   = nrzDiv;
395  r->cfIntDiv= nrzDiv;
396  r->cfIntMod= nrzIntMod;
397  r->cfExactDiv= nrzDiv;
398  r->cfInit = nrzInit;
399  r->cfSize  = nrzSize;
400  r->cfInt  = nrzInt;
401  //#ifdef HAVE_RINGS
402  r->cfDivComp = nrzDivComp; // only for ring stuff
403  r->cfIsUnit = nrzIsUnit; // only for ring stuff
404  r->cfGetUnit = nrzGetUnit; // only for ring stuff
405  r->cfExtGcd = nrzExtGcd; // only for ring stuff
406  r->cfDivBy = nrzDivBy; // only for ring stuff
407  r->cfInit_bigint = nrzMapQ;
408  //#endif
409  r->cfNeg   = nrzNeg;
410  r->cfInvers= nrzInvers;
411  r->cfCopy  = nrzCopy;
412  r->cfWriteLong = nrzWrite;
413  r->cfRead = nrzRead;
414  r->cfGreater = nrzGreater;
415  r->cfEqual = nrzEqual;
416  r->cfIsZero = nrzIsZero;
417  r->cfIsOne = nrzIsOne;
418  r->cfIsMOne = nrzIsMOne;
419  r->cfGreaterZero = nrzGreaterZero;
420  r->cfPower = nrzPower;
421  r->cfGcd  = nrzGcd;
422  r->cfLcm  = nrzLcm;
423  r->cfDelete= nrzDelete;
424  r->cfSetMap = nrzSetMap;
425  r->cfCoeffWrite = nrzCoeffWrite;
426  // debug stuff
427
428#ifdef LDEBUG
429  r->cfDBTest=nrzDBTest;
430#endif
431
432  r->nNULL = 0;
433  r->ch = 0;
434  r->has_simple_Alloc=FALSE;
435  r->has_simple_Inverse=FALSE;
436  return FALSE;
437}
438
439#endif
Note: See TracBrowser for help on using the repository browser.