longrat.cc
Go to the documentation of this file.
1 /****************************************
2 * Computer Algebra System SINGULAR *
3 ****************************************/
4 /*
5 * ABSTRACT: computation with long rational numbers (Hubert Grassmann)
6 */
7 
8 #include <misc/auxiliary.h>
9 #include <omalloc/omalloc.h>
10 
11 #include <factory/factory.h>
12 
13 #include <misc/sirandom.h>
14 #include <misc/prime.h>
15 #include <reporter/reporter.h>
16 
17 #include "rmodulon.h" // ZnmInfo
18 #include "longrat.h"
19 #include "shortfl.h"
20 #include "modulop.h"
21 
22 // allow inlining only from p_Numbers.h and if ! LDEBUG
23 #if defined(DO_LINLINE) && defined(P_NUMBERS_H) && !defined(LDEBUG)
24 #define LINLINE static FORCE_INLINE
25 #else
26 #define LINLINE
27 #undef DO_LINLINE
28 #endif // DO_LINLINE
29 
30 LINLINE BOOLEAN nlEqual(number a, number b, const coeffs r);
31 LINLINE number nlInit(long i, const coeffs r);
32 LINLINE BOOLEAN nlIsOne(number a, const coeffs r);
33 LINLINE BOOLEAN nlIsZero(number za, const coeffs r);
34 LINLINE number nlCopy(number a, const coeffs r);
35 LINLINE number nl_Copy(number a, const coeffs r);
36 LINLINE void nlDelete(number *a, const coeffs r);
37 LINLINE number nlNeg(number za, const coeffs r);
38 LINLINE number nlAdd(number la, number li, const coeffs r);
39 LINLINE number nlSub(number la, number li, const coeffs r);
40 LINLINE number nlMult(number a, number b, const coeffs r);
41 LINLINE void nlInpAdd(number &a, number b, const coeffs r);
42 LINLINE void nlInpMult(number &a, number b, const coeffs r);
43 
44 number nlRInit (long i);
45 
46 
47 // number nlInitMPZ(mpz_t m, const coeffs r);
48 // void nlMPZ(mpz_t m, number &n, const coeffs r);
49 
50 void nlNormalize(number &x, const coeffs r);
51 
52 number nlGcd(number a, number b, const coeffs r);
53 number nlExtGcd(number a, number b, number *s, number *t, const coeffs);
54 number nlNormalizeHelper(number a, number b, const coeffs r); /*special routine !*/
55 BOOLEAN nlGreater(number a, number b, const coeffs r);
56 BOOLEAN nlIsMOne(number a, const coeffs r);
57 long nlInt(number &n, const coeffs r);
58 number nlBigInt(number &n);
59 
60 #ifdef HAVE_RINGS
61 number nlMapGMP(number from, const coeffs src, const coeffs dst);
62 #endif
63 
64 BOOLEAN nlGreaterZero(number za, const coeffs r);
65 number nlInvers(number a, const coeffs r);
66 number nlDiv(number a, number b, const coeffs r);
67 number nlExactDiv(number a, number b, const coeffs r);
68 number nlIntDiv(number a, number b, const coeffs r);
69 number nlIntMod(number a, number b, const coeffs r);
70 void nlPower(number x, int exp, number *lu, const coeffs r);
71 const char * nlRead (const char *s, number *a, const coeffs r);
72 void nlWrite(number a, const coeffs r);
73 
74 void nlCoeffWrite(const coeffs r, BOOLEAN details);
75 number nlFarey(number nN, number nP, const coeffs CF);
76 
77 #ifdef LDEBUG
78 BOOLEAN nlDBTest(number a, const char *f, const int l);
79 #endif
80 
81 nMapFunc nlSetMap(const coeffs src, const coeffs dst);
82 
83 // in-place operations
84 void nlInpIntDiv(number &a, number b, const coeffs r);
85 
86 #ifdef LDEBUG
87 #define nlTest(a, r) nlDBTest(a,__FILE__,__LINE__, r)
88 BOOLEAN nlDBTest(number a, const char *f,int l, const coeffs r);
89 #else
90 #define nlTest(a, r) do {} while (0)
91 #endif
92 
93 
94 // 64 bit version:
95 //#if SIZEOF_LONG == 8
96 #if 0
97 #define MAX_NUM_SIZE 60
98 #define POW_2_28 (1L<<60)
99 #define POW_2_28_32 (1L<<28)
100 #define LONG long
101 #else
102 #define MAX_NUM_SIZE 28
103 #define POW_2_28 (1L<<28)
104 #define POW_2_28_32 (1L<<28)
105 #define LONG int
106 #endif
107 
108 
109 static inline number nlShort3(number x) // assume x->s==3
110 {
111  assume(x->s==3);
112  if (mpz_cmp_ui(x->z,0L)==0)
113  {
114  mpz_clear(x->z);
115  FREE_RNUMBER(x);
116  return INT_TO_SR(0);
117  }
118  if (mpz_size1(x->z)<=MP_SMALL)
119  {
120  LONG ui=mpz_get_si(x->z);
121  if ((((ui<<3)>>3)==ui)
122  && (mpz_cmp_si(x->z,(long)ui)==0))
123  {
124  mpz_clear(x->z);
125  FREE_RNUMBER(x);
126  return INT_TO_SR(ui);
127  }
128  }
129  return x;
130 }
131 
132 #ifndef LONGRAT_CC
133 #define LONGRAT_CC
134 
135 #include <string.h>
136 #include <float.h>
137 
138 #include <coeffs/coeffs.h>
139 #include <reporter/reporter.h>
140 #include <omalloc/omalloc.h>
141 
142 #include <coeffs/numbers.h>
143 #include <coeffs/mpr_complex.h>
144 
145 #ifndef BYTES_PER_MP_LIMB
146 #define BYTES_PER_MP_LIMB sizeof(mp_limb_t)
147 #endif
148 
149 //#define SR_HDL(A) ((long)(A))
150 /*#define SR_INT 1L*/
151 /*#define INT_TO_SR(INT) ((number) (((long)INT << 2) + SR_INT))*/
152 // #define SR_TO_INT(SR) (((long)SR) >> 2)
153 
154 #define MP_SMALL 1
155 //#define mpz_isNeg(A) (mpz_cmp_si(A,0L)<0)
156 #define mpz_isNeg(A) ((A)->_mp_size<0)
157 #define mpz_limb_size(A) ((A)->_mp_size)
158 #define mpz_limb_d(A) ((A)->_mp_d)
159 
160 void _nlDelete_NoImm(number *a);
161 
162 /***************************************************************
163  *
164  * Routines which are never inlined by p_Numbers.h
165  *
166  *******************************************************************/
167 #ifndef P_NUMBERS_H
168 
169 number nlShort3_noinline(number x) // assume x->s==3
170 {
171  return nlShort3(x);
172 }
173 
174 
175 #if (__GNU_MP_VERSION*10+__GNU_MP_VERSION_MINOR < 31)
176 void mpz_mul_si (mpz_ptr r, mpz_srcptr s, long int si)
177 {
178  if (si>=0)
179  mpz_mul_ui(r,s,si);
180  else
181  {
182  mpz_mul_ui(r,s,-si);
183  mpz_neg(r,r);
184  }
185 }
186 #endif
187 
188 static number nlMapP(number from, const coeffs src, const coeffs dst)
189 {
190  assume( getCoeffType(src) == n_Zp );
191 
192  number to = nlInit(npInt(from,src), dst); // FIXME? TODO? // extern long npInt (number &n, const coeffs r);
193 
194  return to;
195 }
196 
197 static number nlMapLongR(number from, const coeffs src, const coeffs dst);
198 static number nlMapR(number from, const coeffs src, const coeffs dst);
199 
200 
201 #ifdef HAVE_RINGS
202 /*2
203 * convert from a GMP integer
204 */
205 number nlMapGMP(number from, const coeffs /*src*/, const coeffs /*dst*/)
206 {
207  number z=ALLOC_RNUMBER();
208 #if defined(LDEBUG)
209  z->debug=123456;
210 #endif
211  mpz_init_set(z->z,(mpz_ptr) from);
212  z->s = 3;
213  z=nlShort3(z);
214  return z;
215 }
216 
217 number nlMapZ(number from, const coeffs src, const coeffs dst)
218 {
219  if (SR_HDL(from) & SR_INT)
220  {
221  return from;
222  }
223  return nlMapGMP(from,src,dst);
224 }
225 
226 /*2
227 * convert from an machine long
228 */
229 number nlMapMachineInt(number from, const coeffs /*src*/, const coeffs /*dst*/)
230 {
231  number z=ALLOC_RNUMBER();
232 #if defined(LDEBUG)
233  z->debug=123456;
234 #endif
235  mpz_init_set_ui(z->z,(unsigned long) from);
236  z->s = 3;
237  z=nlShort3(z);
238  return z;
239 }
240 #endif
241 
242 
243 #ifdef LDEBUG
244 BOOLEAN nlDBTest(number a, const char *f,const int l, const coeffs /*r*/)
245 {
246  if (a==NULL)
247  {
248  Print("!!longrat: NULL in %s:%d\n",f,l);
249  return FALSE;
250  }
251  //if ((int)a==1) Print("!! 0x1 as number ? %s %d\n",f,l);
252  if ((((long)a)&3L)==3L)
253  {
254  Print(" !!longrat:ptr(3) in %s:%d\n",f,l);
255  return FALSE;
256  }
257  if ((((long)a)&3L)==1L)
258  {
259  if (((((LONG)(long)a)<<1)>>1)!=((LONG)(long)a))
260  {
261  Print(" !!longrat:arith:%lx in %s:%d\n",(long)a, f,l);
262  return FALSE;
263  }
264  return TRUE;
265  }
266  /* TODO: If next line is active, then computations in algebraic field
267  extensions over Q will throw a lot of assume violations although
268  everything is computed correctly and no seg fault appears.
269  Maybe the test is not appropriate in this case. */
270  omCheckIf(omCheckAddrSize(a,sizeof(*a)), return FALSE);
271  if (a->debug!=123456)
272  {
273  Print("!!longrat:debug:%d in %s:%d\n",a->debug,f,l);
274  a->debug=123456;
275  return FALSE;
276  }
277  if ((a->s<0)||(a->s>4))
278  {
279  Print("!!longrat:s=%d in %s:%d\n",a->s,f,l);
280  return FALSE;
281  }
282  /* TODO: If next line is active, then computations in algebraic field
283  extensions over Q will throw a lot of assume violations although
284  everything is computed correctly and no seg fault appears.
285  Maybe the test is not appropriate in this case. */
286  //omCheckAddrSize(a->z[0]._mp_d,a->z[0]._mp_alloc*BYTES_PER_MP_LIMB);
287  if (a->z[0]._mp_alloc==0)
288  Print("!!longrat:z->alloc=0 in %s:%d\n",f,l);
289 
290  if (a->s<2)
291  {
292  if ((a->n[0]._mp_d[0]==0)&&(a->n[0]._mp_alloc<=1))
293  {
294  Print("!!longrat: n==0 in %s:%d\n",f,l);
295  return FALSE;
296  }
297  /* TODO: If next line is active, then computations in algebraic field
298  extensions over Q will throw a lot of assume violations although
299  everything is computed correctly and no seg fault appears.
300  Maybe the test is not appropriate in this case. */
301  //omCheckIf(omCheckAddrSize(a->n[0]._mp_d,a->n[0]._mp_alloc*BYTES_PER_MP_LIMB), return FALSE);
302  if (a->z[0]._mp_alloc==0)
303  Print("!!longrat:n->alloc=0 in %s:%d\n",f,l);
304  if ((mpz_size1(a->n) ==1) && (mpz_cmp_si(a->n,1L)==0))
305  {
306  Print("!!longrat:integer as rational in %s:%d\n",f,l);
307  mpz_clear(a->n); a->s=3;
308  return FALSE;
309  }
310  else if (mpz_isNeg(a->n))
311  {
312  Print("!!longrat:div. by negative in %s:%d\n",f,l);
313  mpz_neg(a->z,a->z);
314  mpz_neg(a->n,a->n);
315  return FALSE;
316  }
317  return TRUE;
318  }
319  //if (a->s==2)
320  //{
321  // Print("!!longrat:s=2 in %s:%d\n",f,l);
322  // return FALSE;
323  //}
324  if (mpz_size1(a->z)>MP_SMALL) return TRUE;
325  LONG ui=(LONG)mpz_get_si(a->z);
326  if ((((ui<<3)>>3)==ui)
327  && (mpz_cmp_si(a->z,(long)ui)==0))
328  {
329  Print("!!longrat:im int %d in %s:%d\n",ui,f,l);
330  return FALSE;
331  }
332  return TRUE;
333 }
334 #endif
335 
336 static CanonicalForm nlConvSingNFactoryN( number n, const BOOLEAN setChar, const coeffs /*r*/ )
337 {
338  if (setChar) setCharacteristic( 0 );
339 
341  if ( SR_HDL(n) & SR_INT )
342  {
343  long nn=SR_TO_INT(n);
344  term = nn;
345  }
346  else
347  {
348  if ( n->s == 3 )
349  {
350  mpz_t dummy;
351  long lz=mpz_get_si(n->z);
352  if (mpz_cmp_si(n->z,lz)==0) term=lz;
353  else
354  {
355  mpz_init_set( dummy,n->z );
356  term = make_cf( dummy );
357  }
358  }
359  else
360  {
361  // assume s==0 or s==1
362  mpz_t num, den;
363  On(SW_RATIONAL);
364  mpz_init_set( num, n->z );
365  mpz_init_set( den, n->n );
366  term = make_cf( num, den, ( n->s != 1 ));
367  }
368  }
369  return term;
370 }
371 
372 number nlRInit (long i);
373 
374 static number nlConvFactoryNSingN( const CanonicalForm f, const coeffs r)
375 {
376  if (f.isImm())
377  {
378  return nlInit(f.intval(),r);
379  }
380  else
381  {
382  number z = ALLOC_RNUMBER();
383 #if defined(LDEBUG)
384  z->debug=123456;
385 #endif
386  gmp_numerator( f, z->z );
387  if ( f.den().isOne() )
388  {
389  z->s = 3;
390  z=nlShort3(z);
391  }
392  else
393  {
394  gmp_denominator( f, z->n );
395  z->s = 1;
396  }
397  return z;
398  }
399 }
400 
401 static number nlMapR(number from, const coeffs src, const coeffs dst)
402 {
403  assume( getCoeffType(src) == n_R );
404 
405  double f=nrFloat(from); // FIXME? TODO? // extern float nrFloat(number n);
406  if (f==0.0) return INT_TO_SR(0);
407  int f_sign=1;
408  if (f<0.0)
409  {
410  f_sign=-1;
411  f=-f;
412  }
413  int i=0;
414  mpz_t h1;
415  mpz_init_set_ui(h1,1);
416  while((FLT_RADIX*f) < DBL_MAX && i<DBL_MANT_DIG)
417  {
418  f*=FLT_RADIX;
419  mpz_mul_ui(h1,h1,FLT_RADIX);
420  i++;
421  }
422  number re=nlRInit(1);
423  mpz_set_d(re->z,f);
424  memcpy(&(re->n),&h1,sizeof(h1));
425  re->s=0; /* not normalized */
426  if(f_sign==-1) re=nlNeg(re,dst);
427  nlNormalize(re,dst);
428  return re;
429 }
430 
431 static number nlMapLongR(number from, const coeffs src, const coeffs dst)
432 {
433  assume( getCoeffType(src) == n_long_R );
434 
435  gmp_float *ff=(gmp_float*)from;
436  mpf_t *f=ff->_mpfp();
437  number res;
438  mpz_ptr dest,ndest;
439  int size, i,negative;
440  int e,al,bl;
441  mp_ptr qp,dd,nn;
442 
443  size = (*f)[0]._mp_size;
444  if (size == 0)
445  return INT_TO_SR(0);
446  if(size<0)
447  {
448  negative = 1;
449  size = -size;
450  }
451  else
452  negative = 0;
453 
454  qp = (*f)[0]._mp_d;
455  while(qp[0]==0)
456  {
457  qp++;
458  size--;
459  }
460 
461  e=(*f)[0]._mp_exp-size;
462  res = ALLOC_RNUMBER();
463 #if defined(LDEBUG)
464  res->debug=123456;
465 #endif
466  dest = res->z;
467 
468  void* (*allocfunc) (size_t);
469  mp_get_memory_functions (&allocfunc,NULL, NULL);
470  if (e<0)
471  {
472  al = dest->_mp_size = size;
473  if (al<2) al = 2;
474  dd = (mp_ptr)allocfunc(sizeof(mp_limb_t)*al);
475  for (i=0;i<size;i++) dd[i] = qp[i];
476  bl = 1-e;
477  nn = (mp_ptr)allocfunc(sizeof(mp_limb_t)*bl);
478  nn[bl-1] = 1;
479  ndest = res->n;
480  ndest->_mp_d = nn;
481  ndest->_mp_alloc = ndest->_mp_size = bl;
482  res->s = 0;
483  }
484  else
485  {
486  al = dest->_mp_size = size+e;
487  if (al<2) al = 2;
488  dd = (mp_ptr)allocfunc(sizeof(mp_limb_t)*al);
489  for (i=0;i<size;i++) dd[i+e] = qp[i];
490  for (i=0;i<e;i++) dd[i] = 0;
491  res->s = 3;
492  }
493 
494  dest->_mp_d = dd;
495  dest->_mp_alloc = al;
496  if (negative) mpz_neg(dest,dest);
497 
498  if (res->s==0)
499  nlNormalize(res,dst);
500  else if (mpz_size1(res->z)<=MP_SMALL)
501  {
502  // res is new, res->ref is 1
503  res=nlShort3(res);
504  }
505  nlTest(res, dst);
506  return res;
507 }
508 
509 //static number nlMapLongR(number from)
510 //{
511 // gmp_float *ff=(gmp_float*)from;
512 // const mpf_t *f=ff->mpfp();
513 // int f_size=ABS((*f)[0]._mp_size);
514 // if (f_size==0)
515 // return nlInit(0);
516 // int f_sign=1;
517 // number work=ngcCopy(from);
518 // if (!ngcGreaterZero(work))
519 // {
520 // f_sign=-1;
521 // work=ngcNeg(work);
522 // }
523 // int i=0;
524 // mpz_t h1;
525 // mpz_init_set_ui(h1,1);
526 // while((FLT_RADIX*f) < DBL_MAX && i<DBL_MANT_DIG)
527 // {
528 // f*=FLT_RADIX;
529 // mpz_mul_ui(h1,h1,FLT_RADIX);
530 // i++;
531 // }
532 // number r=nlRInit(1);
533 // mpz_set_d(&(r->z),f);
534 // memcpy(&(r->n),&h1,sizeof(h1));
535 // r->s=0; /* not normalized */
536 // nlNormalize(r);
537 // return r;
538 //
539 //
540 // number r=nlRInit(1);
541 // int f_shift=f_size+(*f)[0]._mp_exp;
542 // if ( f_shift > 0)
543 // {
544 // r->s=0;
545 // mpz_init(&r->n);
546 // mpz_setbit(&r->n,f_shift*BYTES_PER_MP_LIMB*8);
547 // mpz_setbit(&r->z,f_size*BYTES_PER_MP_LIMB*8-1);
548 // // now r->z has enough space
549 // memcpy(mpz_limb_d(&r->z),((*f)[0]._mp_d),f_size*BYTES_PER_MP_LIMB);
550 // nlNormalize(r);
551 // }
552 // else
553 // {
554 // r->s=3;
555 // if (f_shift==0)
556 // {
557 // mpz_setbit(&r->z,f_size*BYTES_PER_MP_LIMB*8-1);
558 // // now r->z has enough space
559 // memcpy(mpz_limb_d(&r->z),((*f)[0]._mp_d),f_size*BYTES_PER_MP_LIMB);
560 // }
561 // else /* f_shift < 0 */
562 // {
563 // mpz_setbit(&r->z,(f_size-f_shift)*BYTES_PER_MP_LIMB*8-1);
564 // // now r->z has enough space
565 // memcpy(mpz_limb_d(&r->z)-f_shift,((*f)[0]._mp_d),
566 // f_size*BYTES_PER_MP_LIMB);
567 // }
568 // }
569 // if ((*f)[0]._mp_size<0);
570 // r=nlNeg(r);
571 // return r;
572 //}
573 
574 int nlSize(number a, const coeffs)
575 {
576  if (a==INT_TO_SR(0))
577  return 0; /* rational 0*/
578  if (SR_HDL(a) & SR_INT)
579  return 1; /* immediate int */
580  int s=a->z[0]._mp_alloc;
581 // while ((s>0) &&(a->z._mp_d[s]==0L)) s--;
582 //#if SIZEOF_LONG == 8
583 // if (a->z._mp_d[s] < (unsigned long)0x100000000L) s=s*2-1;
584 // else s *=2;
585 //#endif
586 // s++;
587  if (a->s<2)
588  {
589  int d=a->n[0]._mp_alloc;
590 // while ((d>0) && (a->n._mp_d[d]==0L)) d--;
591 //#if SIZEOF_LONG == 8
592 // if (a->n._mp_d[d] < (unsigned long)0x100000000L) d=d*2-1;
593 // else d *=2;
594 //#endif
595  s+=d;
596  }
597  return s;
598 }
599 
600 /*2
601 * convert number to int
602 */
603 long nlInt(number &i, const coeffs r)
604 {
605  nlTest(i, r);
606  nlNormalize(i,r);
607  if (SR_HDL(i) & SR_INT)
608  {
609  return SR_TO_INT(i);
610  }
611  if (i->s==3)
612  {
613  if(mpz_size1(i->z)>MP_SMALL) return 0;
614  long ul=mpz_get_si(i->z);
615  if (mpz_cmp_si(i->z,ul)!=0) return 0;
616  return ul;
617  }
618  mpz_t tmp;
619  long ul;
620  mpz_init(tmp);
621  mpz_tdiv_q(tmp,i->z,i->n);
622  if(mpz_size1(tmp)>MP_SMALL) ul=0;
623  else
624  {
625  ul=mpz_get_si(tmp);
626  if (mpz_cmp_si(tmp,ul)!=0) ul=0;
627  }
628  mpz_clear(tmp);
629  return ul;
630 }
631 
632 /*2
633 * convert number to bigint
634 */
635 number nlBigInt(number &i, const coeffs r)
636 {
637  nlTest(i, r);
638  nlNormalize(i,r);
639  if (SR_HDL(i) & SR_INT) return (i);
640  if (i->s==3)
641  {
642  return nlCopy(i,r);
643  }
644  number tmp=nlRInit(1);
645  mpz_tdiv_q(tmp->z,i->z,i->n);
646  tmp=nlShort3(tmp);
647  return tmp;
648 }
649 
650 /*
651 * 1/a
652 */
653 number nlInvers(number a, const coeffs r)
654 {
655  nlTest(a, r);
656  number n;
657  if (SR_HDL(a) & SR_INT)
658  {
659  if ((a==INT_TO_SR(1L)) || (a==INT_TO_SR(-1L)))
660  {
661  return a;
662  }
663  if (nlIsZero(a,r))
664  {
665  WerrorS(nDivBy0);
666  return INT_TO_SR(0);
667  }
668  n=ALLOC_RNUMBER();
669 #if defined(LDEBUG)
670  n->debug=123456;
671 #endif
672  n->s=1;
673  if (((long)a)>0L)
674  {
675  mpz_init_set_ui(n->z,1L);
676  mpz_init_set_si(n->n,(long)SR_TO_INT(a));
677  }
678  else
679  {
680  mpz_init_set_si(n->z,-1L);
681  mpz_init_set_si(n->n,(long)-SR_TO_INT(a));
682  }
683  nlTest(n, r);
684  return n;
685  }
686  n=ALLOC_RNUMBER();
687 #if defined(LDEBUG)
688  n->debug=123456;
689 #endif
690  {
691  mpz_init_set(n->n,a->z);
692  switch (a->s)
693  {
694  case 0:
695  case 1:
696  n->s=a->s;
697  mpz_init_set(n->z,a->n);
698  if (mpz_isNeg(n->n)) /* && n->s<2*/
699  {
700  mpz_neg(n->z,n->z);
701  mpz_neg(n->n,n->n);
702  }
703  if (mpz_cmp_ui(n->n,1L)==0)
704  {
705  mpz_clear(n->n);
706  n->s=3;
707  n=nlShort3(n);
708  }
709  break;
710  case 3:
711  // i.e. |a| > 2^...
712  n->s=1;
713  if (mpz_isNeg(n->n)) /* && n->s<2*/
714  {
715  mpz_neg(n->n,n->n);
716  mpz_init_set_si(n->z,-1L);
717  }
718  else
719  {
720  mpz_init_set_ui(n->z,1L);
721  }
722  break;
723  }
724  }
725  nlTest(n, r);
726  return n;
727 }
728 
729 
730 /*2
731 * u := a / b in Z, if b | a (else undefined)
732 */
733 number nlExactDiv(number a, number b, const coeffs r)
734 {
735  if (b==INT_TO_SR(0))
736  {
737  WerrorS(nDivBy0);
738  return INT_TO_SR(0);
739  }
740  if (a==INT_TO_SR(0))
741  return INT_TO_SR(0);
742  number u;
743  if (SR_HDL(a) & SR_HDL(b) & SR_INT)
744  {
745  /* the small int -(1<<28) divided by -1 is the large int (1<<28) */
746  if ((a==INT_TO_SR(-(POW_2_28)))&&(b==INT_TO_SR(-1L)))
747  {
748  return nlRInit(POW_2_28);
749  }
750  long aa=SR_TO_INT(a);
751  long bb=SR_TO_INT(b);
752  return INT_TO_SR(aa/bb);
753  }
754  number aa=NULL;
755  number bb=NULL;
756  if (SR_HDL(a) & SR_INT)
757  {
758  aa=nlRInit(SR_TO_INT(a));
759  a=aa;
760  }
761  if (SR_HDL(b) & SR_INT)
762  {
763  bb=nlRInit(SR_TO_INT(b));
764  b=bb;
765  }
766  u=ALLOC_RNUMBER();
767 #if defined(LDEBUG)
768  u->debug=123456;
769 #endif
770  mpz_init(u->z);
771  /* u=a/b */
772  u->s = 3;
773  assume(a->s==3);
774  assume(b->s==3);
775  mpz_divexact(u->z,a->z,b->z);
776  if (aa!=NULL)
777  {
778  mpz_clear(aa->z);
779 #if defined(LDEBUG)
780  aa->debug=654324;
781 #endif
782  FREE_RNUMBER(aa); // omFreeBin((void *)aa, rnumber_bin);
783  }
784  if (bb!=NULL)
785  {
786  mpz_clear(bb->z);
787 #if defined(LDEBUG)
788  bb->debug=654324;
789 #endif
790  FREE_RNUMBER(bb); // omFreeBin((void *)bb, rnumber_bin);
791  }
792  u=nlShort3(u);
793  nlTest(u, r);
794  return u;
795 }
796 
797 /*2
798 * u := a / b in Z
799 */
800 number nlIntDiv (number a, number b, const coeffs r)
801 {
802  if (b==INT_TO_SR(0))
803  {
804  WerrorS(nDivBy0);
805  return INT_TO_SR(0);
806  }
807  if (a==INT_TO_SR(0))
808  return INT_TO_SR(0);
809  number u;
810  if (SR_HDL(a) & SR_HDL(b) & SR_INT)
811  {
812  /* the small int -(1<<28) divided by -1 is the large int (1<<28) */
813  if ((a==INT_TO_SR(-(POW_2_28)))&&(b==INT_TO_SR(-1L)))
814  {
815  return nlRInit(POW_2_28);
816  }
817  LONG aa=SR_TO_INT(a);
818  LONG bb=SR_TO_INT(b);
819  LONG rr=aa%bb;
820  if (rr<0) rr+=ABS(bb);
821  LONG cc=(aa-rr)/bb;
822  return INT_TO_SR(cc);
823  }
824  number aa=NULL;
825  if (SR_HDL(a) & SR_INT)
826  {
827  /* the small int -(1<<28) divided by 2^28 is 1 */
828  if (a==INT_TO_SR(-(POW_2_28)))
829  {
830  if(mpz_cmp_si(b->z,(POW_2_28))==0)
831  {
832  return INT_TO_SR(-1);
833  }
834  }
835  aa=nlRInit(SR_TO_INT(a));
836  a=aa;
837  }
838  number bb=NULL;
839  if (SR_HDL(b) & SR_INT)
840  {
841  bb=nlRInit(SR_TO_INT(b));
842  b=bb;
843  }
844  u=ALLOC_RNUMBER();
845 #if defined(LDEBUG)
846  u->debug=123456;
847 #endif
848  assume(a->s==3);
849  assume(b->s==3);
850  mpz_init_set(u->z,a->z);
851  /* u=u/b */
852  u->s = 3;
853  number rr=nlIntMod(a,b,r);
854  if (SR_HDL(rr) & SR_INT) mpz_sub_ui(u->z,u->z,SR_TO_INT(rr));
855  else mpz_sub(u->z,u->z,rr->z);
856  mpz_divexact(u->z,u->z,b->z);
857  if (aa!=NULL)
858  {
859  mpz_clear(aa->z);
860 #if defined(LDEBUG)
861  aa->debug=654324;
862 #endif
863  FREE_RNUMBER(aa);
864  }
865  if (bb!=NULL)
866  {
867  mpz_clear(bb->z);
868 #if defined(LDEBUG)
869  bb->debug=654324;
870 #endif
871  FREE_RNUMBER(bb);
872  }
873  u=nlShort3(u);
874  nlTest(u,r);
875  return u;
876 }
877 
878 /*2
879 * u := a mod b in Z, u>=0
880 */
881 number nlIntMod (number a, number b, const coeffs r)
882 {
883  if (b==INT_TO_SR(0))
884  {
885  WerrorS(nDivBy0);
886  return INT_TO_SR(0);
887  }
888  if (a==INT_TO_SR(0))
889  return INT_TO_SR(0);
890  number u;
891  if (SR_HDL(a) & SR_HDL(b) & SR_INT)
892  {
893  LONG aa=SR_TO_INT(a);
894  LONG bb=SR_TO_INT(b);
895  LONG c=aa % bb;
896  if (c<0) c+=ABS(bb);
897  return INT_TO_SR(c);
898  }
899  if (SR_HDL(a) & SR_INT)
900  {
901  LONG ai=SR_TO_INT(a);
902  mpz_t aa;
903  mpz_init_set_si(aa, ai);
904  u=ALLOC_RNUMBER();
905 #if defined(LDEBUG)
906  u->debug=123456;
907 #endif
908  u->s = 3;
909  mpz_init(u->z);
910  mpz_mod(u->z, aa, b->z);
911  mpz_clear(aa);
912  u=nlShort3(u);
913  nlTest(u,r);
914  return u;
915  }
916  number bb=NULL;
917  if (SR_HDL(b) & SR_INT)
918  {
919  bb=nlRInit(SR_TO_INT(b));
920  b=bb;
921  }
922  u=ALLOC_RNUMBER();
923 #if defined(LDEBUG)
924  u->debug=123456;
925 #endif
926  mpz_init(u->z);
927  u->s = 3;
928  mpz_mod(u->z, a->z, b->z);
929  if (bb!=NULL)
930  {
931  mpz_clear(bb->z);
932 #if defined(LDEBUG)
933  bb->debug=654324;
934 #endif
935  FREE_RNUMBER(bb);
936  }
937  u=nlShort3(u);
938  nlTest(u,r);
939  return u;
940 }
941 
942 BOOLEAN nlDivBy (number a,number b, const coeffs)
943 {
944  if (SR_HDL(a) & SR_HDL(b) & SR_INT)
945  {
946  return ((SR_TO_INT(a) % SR_TO_INT(b))==0);
947  }
948  if (SR_HDL(b) & SR_INT)
949  {
950  return (mpz_divisible_ui_p(a->z,SR_TO_INT(b))!=0);
951  }
952  if (SR_HDL(a) & SR_INT) return FALSE;
953  return mpz_divisible_p(a->z, b->z) != 0;
954 }
955 
956 int nlDivComp(number a, number b, const coeffs r)
957 {
958  if (nlDivBy(a, b, r))
959  {
960  if (nlDivBy(b, a, r)) return 2;
961  return -1;
962  }
963  if (nlDivBy(b, a, r)) return 1;
964  return 0;
965 }
966 
967 number nlGetUnit (number n, const coeffs cf)
968 {
969  if (nlGreaterZero(n,cf)) return INT_TO_SR(1);
970  else return INT_TO_SR(-1);
971 }
972 
973 coeffs nlQuot1(number c, const coeffs r)
974 {
975  long ch = r->cfInt(c, r);
976  int p=IsPrime(ch);
977  coeffs rr=NULL;
978  if (((long)p)==ch)
979  {
980  rr = nInitChar(n_Zp,(void*)ch);
981  }
982  #ifdef HAVE_RINGS
983  else
984  {
985  mpz_t dummy;
986  mpz_init_set_ui(dummy, ch);
987  ZnmInfo info;
988  info.base = dummy;
989  info.exp = (unsigned long) 1;
990  rr = nInitChar(n_Zn, (void*)&info);
991  mpz_clear(dummy);
992  }
993  #endif
994  return(rr);
995 }
996 
997 
998 BOOLEAN nlIsUnit (number a, const coeffs)
999 {
1000  return ((SR_HDL(a) & SR_INT) && (ABS(SR_TO_INT(a))==1));
1001 }
1002 
1003 
1004 /*2
1005 * u := a / b
1006 */
1007 number nlDiv (number a, number b, const coeffs r)
1008 {
1009  if (nlIsZero(b,r))
1010  {
1011  WerrorS(nDivBy0);
1012  return INT_TO_SR(0);
1013  }
1014  number u;
1015 // ---------- short / short ------------------------------------
1016  if (SR_HDL(a) & SR_HDL(b) & SR_INT)
1017  {
1018  LONG i=SR_TO_INT(a);
1019  LONG j=SR_TO_INT(b);
1020  if (j==1L) return a;
1021  if ((i==-POW_2_28) && (j== -1L))
1022  {
1023  return nlRInit(POW_2_28);
1024  }
1025  LONG r=i%j;
1026  if (r==0)
1027  {
1028  return INT_TO_SR(i/j);
1029  }
1030  u=ALLOC_RNUMBER();
1031  u->s=0;
1032  #if defined(LDEBUG)
1033  u->debug=123456;
1034  #endif
1035  mpz_init_set_si(u->z,(long)i);
1036  mpz_init_set_si(u->n,(long)j);
1037  }
1038  else
1039  {
1040  u=ALLOC_RNUMBER();
1041  u->s=0;
1042  #if defined(LDEBUG)
1043  u->debug=123456;
1044  #endif
1045  mpz_init(u->z);
1046 // ---------- short / long ------------------------------------
1047  if (SR_HDL(a) & SR_INT)
1048  {
1049  // short a / (z/n) -> (a*n)/z
1050  if (b->s<2)
1051  {
1052  mpz_mul_si(u->z,b->n,SR_TO_INT(a));
1053  }
1054  else
1055  // short a / long z -> a/z
1056  {
1057  mpz_set_si(u->z,SR_TO_INT(a));
1058  }
1059  if (mpz_cmp(u->z,b->z)==0)
1060  {
1061  mpz_clear(u->z);
1062  FREE_RNUMBER(u);
1063  return INT_TO_SR(1);
1064  }
1065  mpz_init_set(u->n,b->z);
1066  }
1067 // ---------- long / short ------------------------------------
1068  else if (SR_HDL(b) & SR_INT)
1069  {
1070  mpz_set(u->z,a->z);
1071  // (z/n) / b -> z/(n*b)
1072  if (a->s<2)
1073  {
1074  mpz_init_set(u->n,a->n);
1075  if (((long)b)>0L)
1076  mpz_mul_ui(u->n,u->n,SR_TO_INT(b));
1077  else
1078  {
1079  mpz_mul_ui(u->n,u->n,-SR_TO_INT(b));
1080  mpz_neg(u->z,u->z);
1081  }
1082  }
1083  else
1084  // long z / short b -> z/b
1085  {
1086  //mpz_set(u->z,a->z);
1087  mpz_init_set_si(u->n,SR_TO_INT(b));
1088  }
1089  }
1090 // ---------- long / long ------------------------------------
1091  else
1092  {
1093  mpz_set(u->z,a->z);
1094  mpz_init_set(u->n,b->z);
1095  if (a->s<2) mpz_mul(u->n,u->n,a->n);
1096  if (b->s<2) mpz_mul(u->z,u->z,b->n);
1097  }
1098  }
1099  if (mpz_isNeg(u->n))
1100  {
1101  mpz_neg(u->z,u->z);
1102  mpz_neg(u->n,u->n);
1103  }
1104  if (mpz_cmp_si(u->n,1L)==0)
1105  {
1106  mpz_clear(u->n);
1107  u->s=3;
1108  u=nlShort3(u);
1109  }
1110  nlTest(u, r);
1111  return u;
1112 }
1113 
1114 /*2
1115 * u:= x ^ exp
1116 */
1117 void nlPower (number x,int exp,number * u, const coeffs r)
1118 {
1119  *u = INT_TO_SR(0); // 0^e, e!=0
1120  if (exp==0)
1121  *u= INT_TO_SR(1);
1122  else if (!nlIsZero(x,r))
1123  {
1124  nlTest(x, r);
1125  number aa=NULL;
1126  if (SR_HDL(x) & SR_INT)
1127  {
1128  aa=nlRInit(SR_TO_INT(x));
1129  x=aa;
1130  }
1131  else if (x->s==0)
1132  nlNormalize(x,r);
1133  *u=ALLOC_RNUMBER();
1134 #if defined(LDEBUG)
1135  (*u)->debug=123456;
1136 #endif
1137  mpz_init((*u)->z);
1138  mpz_pow_ui((*u)->z,x->z,(unsigned long)exp);
1139  if (x->s<2)
1140  {
1141  if (mpz_cmp_si(x->n,1L)==0)
1142  {
1143  x->s=3;
1144  mpz_clear(x->n);
1145  }
1146  else
1147  {
1148  mpz_init((*u)->n);
1149  mpz_pow_ui((*u)->n,x->n,(unsigned long)exp);
1150  }
1151  }
1152  (*u)->s = x->s;
1153  if ((*u)->s==3) *u=nlShort3(*u);
1154  if (aa!=NULL)
1155  {
1156  mpz_clear(aa->z);
1157  FREE_RNUMBER(aa);
1158  }
1159  }
1160 #ifdef LDEBUG
1161  if (exp<0) Print("nlPower: neg. exp. %d\n",exp);
1162  nlTest(*u, r);
1163 #endif
1164 }
1165 
1166 
1167 /*2
1168 * za >= 0 ?
1169 */
1170 BOOLEAN nlGreaterZero (number a, const coeffs r)
1171 {
1172  nlTest(a, r);
1173  if (SR_HDL(a) & SR_INT) return SR_HDL(a)>1L /* represents number(0) */;
1174  return (!mpz_isNeg(a->z));
1175 }
1176 
1177 /*2
1178 * a > b ?
1179 */
1180 BOOLEAN nlGreater (number a, number b, const coeffs r)
1181 {
1182  nlTest(a, r);
1183  nlTest(b, r);
1184  number re;
1185  BOOLEAN rr;
1186  re=nlSub(a,b,r);
1187  rr=(!nlIsZero(re,r)) && (nlGreaterZero(re,r));
1188  nlDelete(&re,r);
1189  return rr;
1190 }
1191 
1192 /*2
1193 * a == -1 ?
1194 */
1195 BOOLEAN nlIsMOne (number a, const coeffs r)
1196 {
1197 #ifdef LDEBUG
1198  if (a==NULL) return FALSE;
1199  nlTest(a, r);
1200 #endif
1201  return (a==INT_TO_SR(-1L));
1202 }
1203 
1204 /*2
1205 * result =gcd(a,b)
1206 */
1207 number nlGcd(number a, number b, const coeffs r)
1208 {
1209  number result;
1210  nlTest(a, r);
1211  nlTest(b, r);
1212  //nlNormalize(a);
1213  //nlNormalize(b);
1214  if ((a==INT_TO_SR(1L))||(a==INT_TO_SR(-1L))
1215  || (b==INT_TO_SR(1L))||(b==INT_TO_SR(-1L)))
1216  return INT_TO_SR(1L);
1217  if (a==INT_TO_SR(0)) /* gcd(0,b) ->b */
1218  return nlCopy(b,r);
1219  if (b==INT_TO_SR(0)) /* gcd(a,0) -> a */
1220  return nlCopy(a,r);
1221  if (SR_HDL(a) & SR_HDL(b) & SR_INT)
1222  {
1223  long i=SR_TO_INT(a);
1224  long j=SR_TO_INT(b);
1225  if((i==0L)||(j==0L))
1226  return INT_TO_SR(1);
1227  long l;
1228  i=ABS(i);
1229  j=ABS(j);
1230  do
1231  {
1232  l=i%j;
1233  i=j;
1234  j=l;
1235  } while (l!=0L);
1236  if (i==POW_2_28)
1238  else
1239  result=INT_TO_SR(i);
1240  nlTest(result,r);
1241  return result;
1242  }
1243  if (((!(SR_HDL(a) & SR_INT))&&(a->s<2))
1244  || ((!(SR_HDL(b) & SR_INT))&&(b->s<2))) return INT_TO_SR(1);
1245  if (SR_HDL(a) & SR_INT)
1246  {
1247  LONG aa=ABS(SR_TO_INT(a));
1248  unsigned long t=mpz_gcd_ui(NULL,b->z,(long)aa);
1249  if (t==POW_2_28)
1251  else
1252  result=INT_TO_SR(t);
1253  }
1254  else
1255  if (SR_HDL(b) & SR_INT)
1256  {
1257  LONG bb=ABS(SR_TO_INT(b));
1258  unsigned long t=mpz_gcd_ui(NULL,a->z,(long)bb);
1259  if (t==POW_2_28)
1261  else
1262  result=INT_TO_SR(t);
1263  }
1264  else
1265  {
1267  result->s = 3;
1268  #ifdef LDEBUG
1269  result->debug=123456;
1270  #endif
1271  mpz_init(result->z);
1272  mpz_gcd(result->z,a->z,b->z);
1274  }
1275  nlTest(result, r);
1276  return result;
1277 }
1278 static int int_extgcd(int a, int b, int * u, int* x, int * v, int* y)
1279 {
1280  int q, r;
1281  if (a==0)
1282  {
1283  *u = 0;
1284  *v = 1;
1285  *x = -1;
1286  *y = 0;
1287  return b;
1288  }
1289  if (b==0)
1290  {
1291  *u = 1;
1292  *v = 0;
1293  *x = 0;
1294  *y = 1;
1295  return a;
1296  }
1297  *u=1;
1298  *v=0;
1299  *x=0;
1300  *y=1;
1301  do
1302  {
1303  q = a/b;
1304  r = a%b;
1305  assume (q*b+r == a);
1306  a = b;
1307  b = r;
1308 
1309  r = -(*v)*q+(*u);
1310  (*u) =(*v);
1311  (*v) = r;
1312 
1313  r = -(*y)*q+(*x);
1314  (*x) = (*y);
1315  (*y) = r;
1316  } while (b);
1317 
1318  return a;
1319 }
1320 
1321 //number nlGcd_dummy(number a, number b, const coeffs r)
1322 //{
1323 // extern char my_yylinebuf[80];
1324 // Print("nlGcd in >>%s<<\n",my_yylinebuf);
1325 // return nlGcd(a,b,r);;
1326 //}
1327 
1328 number nlShort1(number x) // assume x->s==0/1
1329 {
1330  assume(x->s<2);
1331  if (mpz_cmp_ui(x->z,0L)==0)
1332  {
1333  _nlDelete_NoImm(&x);
1334  return INT_TO_SR(0);
1335  }
1336  if (x->s<2)
1337  {
1338  if (mpz_cmp(x->z,x->n)==0)
1339  {
1340  _nlDelete_NoImm(&x);
1341  return INT_TO_SR(1);
1342  }
1343  }
1344  return x;
1345 }
1346 /*2
1347 * simplify x
1348 */
1349 void nlNormalize (number &x, const coeffs r)
1350 {
1351  if ((SR_HDL(x) & SR_INT) ||(x==NULL))
1352  return;
1353  if (x->s==3)
1354  {
1356  nlTest(x,r);
1357  return;
1358  }
1359  else if (x->s==0)
1360  {
1361  if (mpz_cmp_si(x->n,1L)==0)
1362  {
1363  mpz_clear(x->n);
1364  x->s=3;
1365  x=nlShort3(x);
1366  }
1367  else
1368  {
1369  mpz_t gcd;
1370  mpz_init(gcd);
1371  mpz_gcd(gcd,x->z,x->n);
1372  x->s=1;
1373  if (mpz_cmp_si(gcd,1L)!=0)
1374  {
1375  mpz_divexact(x->z,x->z,gcd);
1376  mpz_divexact(x->n,x->n,gcd);
1377  if (mpz_cmp_si(x->n,1L)==0)
1378  {
1379  mpz_clear(x->n);
1380  x->s=3;
1382  }
1383  }
1384  mpz_clear(gcd);
1385  }
1386  }
1387  nlTest(x, r);
1388 }
1389 
1390 /*2
1391 * returns in result->z the lcm(a->z,b->n)
1392 */
1393 number nlNormalizeHelper(number a, number b, const coeffs r)
1394 {
1395  number result;
1396  nlTest(a, r);
1397  nlTest(b, r);
1398  if ((SR_HDL(b) & SR_INT)
1399  || (b->s==3))
1400  {
1401  // b is 1/(b->n) => b->n is 1 => result is a
1402  return nlCopy(a,r);
1403  }
1405 #if defined(LDEBUG)
1406  result->debug=123456;
1407 #endif
1408  result->s=3;
1409  mpz_t gcd;
1410  mpz_init(gcd);
1411  mpz_init(result->z);
1412  if (SR_HDL(a) & SR_INT)
1413  mpz_gcd_ui(gcd,b->n,ABS(SR_TO_INT(a)));
1414  else
1415  mpz_gcd(gcd,a->z,b->n);
1416  if (mpz_cmp_si(gcd,1L)!=0)
1417  {
1418  mpz_t bt;
1419  mpz_init(bt);
1420  mpz_divexact(bt,b->n,gcd);
1421  if (SR_HDL(a) & SR_INT)
1422  mpz_mul_si(result->z,bt,SR_TO_INT(a));
1423  else
1424  mpz_mul(result->z,bt,a->z);
1425  mpz_clear(bt);
1426  }
1427  else
1428  if (SR_HDL(a) & SR_INT)
1429  mpz_mul_si(result->z,b->n,SR_TO_INT(a));
1430  else
1431  mpz_mul(result->z,b->n,a->z);
1432  mpz_clear(gcd);
1434  nlTest(result, r);
1435  return result;
1436 }
1437 
1438 // Map q \in QQ or ZZ \to Zp or an extension of it
1439 // src = Q or Z, dst = Zp (or an extension of Zp)
1440 number nlModP(number q, const coeffs /*Q*/, const coeffs Zp)
1441 {
1442  const int p = n_GetChar(Zp);
1443  assume( p > 0 );
1444 
1445  const long P = p;
1446  assume( P > 0 );
1447 
1448  // embedded long within q => only long numerator has to be converted
1449  // to int (modulo char.)
1450  if (SR_HDL(q) & SR_INT)
1451  {
1452  long i = SR_TO_INT(q);
1453  return n_Init( i, Zp );
1454  }
1455 
1456  const unsigned long PP = p;
1457 
1458  // numerator modulo char. should fit into int
1459  number z = n_Init( static_cast<long>(mpz_fdiv_ui(q->z, PP)), Zp );
1460 
1461  // denominator != 1?
1462  if (q->s!=3)
1463  {
1464  // denominator modulo char. should fit into int
1465  number n = n_Init( static_cast<long>(mpz_fdiv_ui(q->n, PP)), Zp );
1466 
1467  number res = n_Div( z, n, Zp );
1468 
1469  n_Delete(&z, Zp);
1470  n_Delete(&n, Zp);
1471 
1472  return res;
1473  }
1474 
1475  return z;
1476 }
1477 
1478 #ifdef HAVE_RINGS
1479 /*2
1480 * convert number i (from Q) to GMP and warn if denom != 1
1481 */
1482 void nlGMP(number &i, mpz_t n, const coeffs r)
1483 {
1484  // Hier brauche ich einfach die GMP Zahl
1485  nlTest(i, r);
1486  nlNormalize(i, r);
1487  if (SR_HDL(i) & SR_INT)
1488  {
1489  mpz_set_si(n, SR_TO_INT(i));
1490  return;
1491  }
1492  if (i->s!=3)
1493  {
1494  WarnS("Omitted denominator during coefficient mapping !");
1495  }
1496  mpz_set(n, i->z);
1497 }
1498 #endif
1499 
1500 /*2
1501 * acces to denominator, other 1 for integers
1502 */
1503 number nlGetDenom(number &n, const coeffs r)
1504 {
1505  if (!(SR_HDL(n) & SR_INT))
1506  {
1507  if (n->s==0)
1508  {
1509  nlNormalize(n,r);
1510  }
1511  if (!(SR_HDL(n) & SR_INT))
1512  {
1513  if (n->s!=3)
1514  {
1515  number u=ALLOC_RNUMBER();
1516  u->s=3;
1517 #if defined(LDEBUG)
1518  u->debug=123456;
1519 #endif
1520  mpz_init_set(u->z,n->n);
1521  u=nlShort3_noinline(u);
1522  return u;
1523  }
1524  }
1525  }
1526  return INT_TO_SR(1);
1527 }
1528 
1529 /*2
1530 * acces to Nominator, nlCopy(n) for integers
1531 */
1532 number nlGetNumerator(number &n, const coeffs r)
1533 {
1534  if (!(SR_HDL(n) & SR_INT))
1535  {
1536  if (n->s==0)
1537  {
1538  nlNormalize(n,r);
1539  }
1540  if (!(SR_HDL(n) & SR_INT))
1541  {
1542  number u=ALLOC_RNUMBER();
1543 #if defined(LDEBUG)
1544  u->debug=123456;
1545 #endif
1546  u->s=3;
1547  mpz_init_set(u->z,n->z);
1548  if (n->s!=3)
1549  {
1550  u=nlShort3_noinline(u);
1551  }
1552  return u;
1553  }
1554  }
1555  return n; // imm. int
1556 }
1557 
1558 /***************************************************************
1559  *
1560  * routines which are needed by Inline(d) routines
1561  *
1562  *******************************************************************/
1564 {
1565  assume(! (SR_HDL(a) & SR_HDL(b) & SR_INT));
1566 // long - short
1567  BOOLEAN bo;
1568  if (SR_HDL(b) & SR_INT)
1569  {
1570  if (a->s!=0) return FALSE;
1571  number n=b; b=a; a=n;
1572  }
1573 // short - long
1574  if (SR_HDL(a) & SR_INT)
1575  {
1576  if (b->s!=0)
1577  return FALSE;
1578  if ((((long)a) > 0L) && (mpz_isNeg(b->z)))
1579  return FALSE;
1580  if ((((long)a) < 0L) && (!mpz_isNeg(b->z)))
1581  return FALSE;
1582  mpz_t bb;
1583  mpz_init(bb);
1584  mpz_mul_si(bb,b->n,(long)SR_TO_INT(a));
1585  bo=(mpz_cmp(bb,b->z)==0);
1586  mpz_clear(bb);
1587  return bo;
1588  }
1589 // long - long
1590  if (((a->s==1) && (b->s==3))
1591  || ((b->s==1) && (a->s==3)))
1592  return FALSE;
1593  if (mpz_isNeg(a->z)&&(!mpz_isNeg(b->z)))
1594  return FALSE;
1595  if (mpz_isNeg(b->z)&&(!mpz_isNeg(a->z)))
1596  return FALSE;
1597  mpz_t aa;
1598  mpz_t bb;
1599  mpz_init_set(aa,a->z);
1600  mpz_init_set(bb,b->z);
1601  if (a->s<2) mpz_mul(bb,bb,a->n);
1602  if (b->s<2) mpz_mul(aa,aa,b->n);
1603  bo=(mpz_cmp(aa,bb)==0);
1604  mpz_clear(aa);
1605  mpz_clear(bb);
1606  return bo;
1607 }
1608 
1609 // copy not immediate number a
1610 number _nlCopy_NoImm(number a)
1611 {
1612  assume(!((SR_HDL(a) & SR_INT)||(a==NULL)));
1613  //nlTest(a, r);
1614  number b=ALLOC_RNUMBER();
1615 #if defined(LDEBUG)
1616  b->debug=123456;
1617 #endif
1618  switch (a->s)
1619  {
1620  case 0:
1621  case 1:
1622  mpz_init_set(b->n,a->n);
1623  case 3:
1624  mpz_init_set(b->z,a->z);
1625  break;
1626  }
1627  b->s = a->s;
1628  return b;
1629 }
1630 
1631 void _nlDelete_NoImm(number *a)
1632 {
1633  {
1634  switch ((*a)->s)
1635  {
1636  case 0:
1637  case 1:
1638  mpz_clear((*a)->n);
1639  case 3:
1640  mpz_clear((*a)->z);
1641 #ifdef LDEBUG
1642  (*a)->s=2;
1643 #endif
1644  }
1645  FREE_RNUMBER(*a); // omFreeBin((void *) *a, rnumber_bin);
1646  }
1647 }
1648 
1649 number _nlNeg_NoImm(number a)
1650 {
1651  {
1652  mpz_neg(a->z,a->z);
1653  if (a->s==3)
1654  {
1655  a=nlShort3(a);
1656  }
1657  }
1658  return a;
1659 }
1660 
1661 // conditio to use nlNormalize_Gcd in intermediate computations:
1662 #define GCD_NORM_COND(OLD,NEW) (mpz_size1(NEW->z)>mpz_size1(OLD->z))
1663 
1664 static void nlNormalize_Gcd(number &x)
1665 {
1666  mpz_t gcd;
1667  mpz_init(gcd);
1668  mpz_gcd(gcd,x->z,x->n);
1669  x->s=1;
1670  if (mpz_cmp_si(gcd,1L)!=0)
1671  {
1672  mpz_divexact(x->z,x->z,gcd);
1673  mpz_divexact(x->n,x->n,gcd);
1674  if (mpz_cmp_si(x->n,1L)==0)
1675  {
1676  mpz_clear(x->n);
1677  x->s=3;
1679  }
1680  }
1681  mpz_clear(gcd);
1682 }
1683 
1684 number _nlAdd_aNoImm_OR_bNoImm(number a, number b)
1685 {
1686  number u=ALLOC_RNUMBER();
1687 #if defined(LDEBUG)
1688  u->debug=123456;
1689 #endif
1690  mpz_init(u->z);
1691  if (SR_HDL(b) & SR_INT)
1692  {
1693  number x=a;
1694  a=b;
1695  b=x;
1696  }
1697  if (SR_HDL(a) & SR_INT)
1698  {
1699  switch (b->s)
1700  {
1701  case 0:
1702  case 1:/* a:short, b:1 */
1703  {
1704  mpz_t x;
1705  mpz_init(x);
1706  mpz_mul_si(x,b->n,SR_TO_INT(a));
1707  mpz_add(u->z,b->z,x);
1708  mpz_clear(x);
1709  if (mpz_cmp_ui(u->z,0L)==0)
1710  {
1711  mpz_clear(u->z);
1712  FREE_RNUMBER(u);
1713  return INT_TO_SR(0);
1714  }
1715  if (mpz_cmp(u->z,b->n)==0)
1716  {
1717  mpz_clear(u->z);
1718  FREE_RNUMBER(u);
1719  return INT_TO_SR(1);
1720  }
1721  mpz_init_set(u->n,b->n);
1722  u->s = 0;
1723  if (GCD_NORM_COND(b,u)) { nlNormalize_Gcd(u); }
1724  break;
1725  }
1726  case 3:
1727  {
1728  if (((long)a)>0L)
1729  mpz_add_ui(u->z,b->z,SR_TO_INT(a));
1730  else
1731  mpz_sub_ui(u->z,b->z,-SR_TO_INT(a));
1732  u->s = 3;
1733  u=nlShort3(u);
1734  break;
1735  }
1736  }
1737  }
1738  else
1739  {
1740  switch (a->s)
1741  {
1742  case 0:
1743  case 1:
1744  {
1745  switch(b->s)
1746  {
1747  case 0:
1748  case 1:
1749  {
1750  mpz_t x;
1751  mpz_init(x);
1752 
1753  mpz_mul(x,b->z,a->n);
1754  mpz_mul(u->z,a->z,b->n);
1755  mpz_add(u->z,u->z,x);
1756  mpz_clear(x);
1757 
1758  if (mpz_cmp_ui(u->z,0L)==0)
1759  {
1760  mpz_clear(u->z);
1761  FREE_RNUMBER(u);
1762  return INT_TO_SR(0);
1763  }
1764  mpz_init(u->n);
1765  mpz_mul(u->n,a->n,b->n);
1766  if (mpz_cmp(u->z,u->n)==0)
1767  {
1768  mpz_clear(u->z);
1769  mpz_clear(u->n);
1770  FREE_RNUMBER(u);
1771  return INT_TO_SR(1);
1772  }
1773  u->s = 0;
1774  if (GCD_NORM_COND(b,u)) { nlNormalize_Gcd(u); }
1775  break;
1776  }
1777  case 3: /* a:1 b:3 */
1778  {
1779  mpz_mul(u->z,b->z,a->n);
1780  mpz_add(u->z,u->z,a->z);
1781  if (mpz_cmp_ui(u->z,0L)==0)
1782  {
1783  mpz_clear(u->z);
1784  FREE_RNUMBER(u);
1785  return INT_TO_SR(0);
1786  }
1787  if (mpz_cmp(u->z,a->n)==0)
1788  {
1789  mpz_clear(u->z);
1790  FREE_RNUMBER(u);
1791  return INT_TO_SR(1);
1792  }
1793  mpz_init_set(u->n,a->n);
1794  u->s = 0;
1795  if (GCD_NORM_COND(a,u)) { nlNormalize_Gcd(u); }
1796  break;
1797  }
1798  } /*switch (b->s) */
1799  break;
1800  }
1801  case 3:
1802  {
1803  switch(b->s)
1804  {
1805  case 0:
1806  case 1:/* a:3, b:1 */
1807  {
1808  mpz_mul(u->z,a->z,b->n);
1809  mpz_add(u->z,u->z,b->z);
1810  if (mpz_cmp_ui(u->z,0L)==0)
1811  {
1812  mpz_clear(u->z);
1813  FREE_RNUMBER(u);
1814  return INT_TO_SR(0);
1815  }
1816  if (mpz_cmp(u->z,b->n)==0)
1817  {
1818  mpz_clear(u->z);
1819  FREE_RNUMBER(u);
1820  return INT_TO_SR(1);
1821  }
1822  mpz_init_set(u->n,b->n);
1823  u->s = 0;
1824  if (GCD_NORM_COND(b,u)) { nlNormalize_Gcd(u); }
1825  break;
1826  }
1827  case 3:
1828  {
1829  mpz_add(u->z,a->z,b->z);
1830  u->s = 3;
1831  u=nlShort3(u);
1832  break;
1833  }
1834  }
1835  break;
1836  }
1837  }
1838  }
1839  return u;
1840 }
1841 
1842 void _nlInpAdd_aNoImm_OR_bNoImm(number &a, number b)
1843 {
1844  if (SR_HDL(b) & SR_INT)
1845  {
1846  switch (a->s)
1847  {
1848  case 0:
1849  case 1:/* b:short, a:1 */
1850  {
1851  mpz_t x;
1852  mpz_init(x);
1853  mpz_mul_si(x,a->n,SR_TO_INT(b));
1854  mpz_add(a->z,a->z,x);
1855  mpz_clear(x);
1856  nlNormalize_Gcd(a);
1857  break;
1858  }
1859  case 3:
1860  {
1861  if (((long)b)>0L)
1862  mpz_add_ui(a->z,a->z,SR_TO_INT(b));
1863  else
1864  mpz_sub_ui(a->z,a->z,-SR_TO_INT(b));
1865  a->s = 3;
1867  break;
1868  }
1869  }
1870  return;
1871  }
1872  else if (SR_HDL(a) & SR_INT)
1873  {
1874  number u=ALLOC_RNUMBER();
1875  #if defined(LDEBUG)
1876  u->debug=123456;
1877  #endif
1878  mpz_init(u->z);
1879  switch (b->s)
1880  {
1881  case 0:
1882  case 1:/* a:short, b:1 */
1883  {
1884  mpz_t x;
1885  mpz_init(x);
1886 
1887  mpz_mul_si(x,b->n,SR_TO_INT(a));
1888  mpz_add(u->z,b->z,x);
1889  mpz_clear(x);
1890  // result cannot be 0, if coeffs are normalized
1891  mpz_init_set(u->n,b->n);
1892  u->s=0;
1893  if (GCD_NORM_COND(b,u)) { nlNormalize_Gcd(u); }
1894  else { u=nlShort1(u); }
1895  break;
1896  }
1897  case 3:
1898  {
1899  if (((long)a)>0L)
1900  mpz_add_ui(u->z,b->z,SR_TO_INT(a));
1901  else
1902  mpz_sub_ui(u->z,b->z,-SR_TO_INT(a));
1903  // result cannot be 0, if coeffs are normalized
1904  u->s = 3;
1905  u=nlShort3_noinline(u);
1906  break;
1907  }
1908  }
1909  a=u;
1910  }
1911  else
1912  {
1913  switch (a->s)
1914  {
1915  case 0:
1916  case 1:
1917  {
1918  switch(b->s)
1919  {
1920  case 0:
1921  case 1: /* a:1 b:1 */
1922  {
1923  mpz_t x;
1924  mpz_t y;
1925  mpz_init(x);
1926  mpz_init(y);
1927  mpz_mul(x,b->z,a->n);
1928  mpz_mul(y,a->z,b->n);
1929  mpz_add(a->z,x,y);
1930  mpz_clear(x);
1931  mpz_clear(y);
1932  mpz_mul(a->n,a->n,b->n);
1933  a->s=0;
1934  if (GCD_NORM_COND(b,a)) { nlNormalize_Gcd(a); }
1935  else { a=nlShort1(a);}
1936  break;
1937  }
1938  case 3: /* a:1 b:3 */
1939  {
1940  mpz_t x;
1941  mpz_init(x);
1942  mpz_mul(x,b->z,a->n);
1943  mpz_add(a->z,a->z,x);
1944  mpz_clear(x);
1945  a->s=0;
1946  if (GCD_NORM_COND(b,a)) { nlNormalize_Gcd(a); }
1947  else { a=nlShort1(a);}
1948  break;
1949  }
1950  } /*switch (b->s) */
1951  break;
1952  }
1953  case 3:
1954  {
1955  switch(b->s)
1956  {
1957  case 0:
1958  case 1:/* a:3, b:1 */
1959  {
1960  mpz_t x;
1961  mpz_init(x);
1962  mpz_mul(x,a->z,b->n);
1963  mpz_add(a->z,b->z,x);
1964  mpz_clear(x);
1965  mpz_init_set(a->n,b->n);
1966  a->s=0;
1967  if (GCD_NORM_COND(b,a)) { nlNormalize_Gcd(a); }
1968  else { a=nlShort1(a);}
1969  break;
1970  }
1971  case 3:
1972  {
1973  mpz_add(a->z,a->z,b->z);
1974  a->s = 3;
1976  break;
1977  }
1978  }
1979  break;
1980  }
1981  }
1982  }
1983 }
1984 
1985 number _nlSub_aNoImm_OR_bNoImm(number a, number b)
1986 {
1987  number u=ALLOC_RNUMBER();
1988 #if defined(LDEBUG)
1989  u->debug=123456;
1990 #endif
1991  mpz_init(u->z);
1992  if (SR_HDL(a) & SR_INT)
1993  {
1994  switch (b->s)
1995  {
1996  case 0:
1997  case 1:/* a:short, b:1 */
1998  {
1999  mpz_t x;
2000  mpz_init(x);
2001  mpz_mul_si(x,b->n,SR_TO_INT(a));
2002  mpz_sub(u->z,x,b->z);
2003  mpz_clear(x);
2004  if (mpz_cmp_ui(u->z,0L)==0)
2005  {
2006  mpz_clear(u->z);
2007  FREE_RNUMBER(u);
2008  return INT_TO_SR(0);
2009  }
2010  if (mpz_cmp(u->z,b->n)==0)
2011  {
2012  mpz_clear(u->z);
2013  FREE_RNUMBER(u);
2014  return INT_TO_SR(1);
2015  }
2016  mpz_init_set(u->n,b->n);
2017  u->s=0;
2018  if (GCD_NORM_COND(b,u)) { nlNormalize_Gcd(u); }
2019  break;
2020  }
2021  case 3:
2022  {
2023  if (((long)a)>0L)
2024  {
2025  mpz_sub_ui(u->z,b->z,SR_TO_INT(a));
2026  mpz_neg(u->z,u->z);
2027  }
2028  else
2029  {
2030  mpz_add_ui(u->z,b->z,-SR_TO_INT(a));
2031  mpz_neg(u->z,u->z);
2032  }
2033  u->s = 3;
2034  u=nlShort3(u);
2035  break;
2036  }
2037  }
2038  }
2039  else if (SR_HDL(b) & SR_INT)
2040  {
2041  switch (a->s)
2042  {
2043  case 0:
2044  case 1:/* b:short, a:1 */
2045  {
2046  mpz_t x;
2047  mpz_init(x);
2048  mpz_mul_si(x,a->n,SR_TO_INT(b));
2049  mpz_sub(u->z,a->z,x);
2050  mpz_clear(x);
2051  if (mpz_cmp_ui(u->z,0L)==0)
2052  {
2053  mpz_clear(u->z);
2054  FREE_RNUMBER(u);
2055  return INT_TO_SR(0);
2056  }
2057  if (mpz_cmp(u->z,a->n)==0)
2058  {
2059  mpz_clear(u->z);
2060  FREE_RNUMBER(u);
2061  return INT_TO_SR(1);
2062  }
2063  mpz_init_set(u->n,a->n);
2064  u->s=0;
2065  if (GCD_NORM_COND(a,u)) { nlNormalize_Gcd(u); }
2066  break;
2067  }
2068  case 3:
2069  {
2070  if (((long)b)>0L)
2071  {
2072  mpz_sub_ui(u->z,a->z,SR_TO_INT(b));
2073  }
2074  else
2075  {
2076  mpz_add_ui(u->z,a->z,-SR_TO_INT(b));
2077  }
2078  u->s = 3;
2079  u=nlShort3(u);
2080  break;
2081  }
2082  }
2083  }
2084  else
2085  {
2086  switch (a->s)
2087  {
2088  case 0:
2089  case 1:
2090  {
2091  switch(b->s)
2092  {
2093  case 0:
2094  case 1:
2095  {
2096  mpz_t x;
2097  mpz_t y;
2098  mpz_init(x);
2099  mpz_init(y);
2100  mpz_mul(x,b->z,a->n);
2101  mpz_mul(y,a->z,b->n);
2102  mpz_sub(u->z,y,x);
2103  mpz_clear(x);
2104  mpz_clear(y);
2105  if (mpz_cmp_ui(u->z,0L)==0)
2106  {
2107  mpz_clear(u->z);
2108  FREE_RNUMBER(u);
2109  return INT_TO_SR(0);
2110  }
2111  mpz_init(u->n);
2112  mpz_mul(u->n,a->n,b->n);
2113  if (mpz_cmp(u->z,u->n)==0)
2114  {
2115  mpz_clear(u->z);
2116  mpz_clear(u->n);
2117  FREE_RNUMBER(u);
2118  return INT_TO_SR(1);
2119  }
2120  u->s=0;
2121  if (GCD_NORM_COND(a,u)) { nlNormalize_Gcd(u); }
2122  break;
2123  }
2124  case 3: /* a:1, b:3 */
2125  {
2126  mpz_t x;
2127  mpz_init(x);
2128  mpz_mul(x,b->z,a->n);
2129  mpz_sub(u->z,a->z,x);
2130  mpz_clear(x);
2131  if (mpz_cmp_ui(u->z,0L)==0)
2132  {
2133  mpz_clear(u->z);
2134  FREE_RNUMBER(u);
2135  return INT_TO_SR(0);
2136  }
2137  if (mpz_cmp(u->z,a->n)==0)
2138  {
2139  mpz_clear(u->z);
2140  FREE_RNUMBER(u);
2141  return INT_TO_SR(1);
2142  }
2143  mpz_init_set(u->n,a->n);
2144  u->s=0;
2145  if (GCD_NORM_COND(a,u)) { nlNormalize_Gcd(u); }
2146  break;
2147  }
2148  }
2149  break;
2150  }
2151  case 3:
2152  {
2153  switch(b->s)
2154  {
2155  case 0:
2156  case 1: /* a:3, b:1 */
2157  {
2158  mpz_t x;
2159  mpz_init(x);
2160  mpz_mul(x,a->z,b->n);
2161  mpz_sub(u->z,x,b->z);
2162  mpz_clear(x);
2163  if (mpz_cmp_ui(u->z,0L)==0)
2164  {
2165  mpz_clear(u->z);
2166  FREE_RNUMBER(u);
2167  return INT_TO_SR(0);
2168  }
2169  if (mpz_cmp(u->z,b->n)==0)
2170  {
2171  mpz_clear(u->z);
2172  FREE_RNUMBER(u);
2173  return INT_TO_SR(1);
2174  }
2175  mpz_init_set(u->n,b->n);
2176  u->s=0;
2177  if (GCD_NORM_COND(b,u)) { nlNormalize_Gcd(u); }
2178  break;
2179  }
2180  case 3: /* a:3 , b:3 */
2181  {
2182  mpz_sub(u->z,a->z,b->z);
2183  u->s = 3;
2184  u=nlShort3(u);
2185  break;
2186  }
2187  }
2188  break;
2189  }
2190  }
2191  }
2192  return u;
2193 }
2194 
2195 // a and b are intermediate, but a*b not
2196 number _nlMult_aImm_bImm_rNoImm(number a, number b)
2197 {
2198  number u=ALLOC_RNUMBER();
2199 #if defined(LDEBUG)
2200  u->debug=123456;
2201 #endif
2202  u->s=3;
2203  mpz_init_set_si(u->z,SR_TO_INT(a));
2204  mpz_mul_si(u->z,u->z,SR_TO_INT(b));
2205  return u;
2206 }
2207 
2208 // a or b are not immediate
2209 number _nlMult_aNoImm_OR_bNoImm(number a, number b)
2210 {
2211  assume(! (SR_HDL(a) & SR_HDL(b) & SR_INT));
2212  number u=ALLOC_RNUMBER();
2213 #if defined(LDEBUG)
2214  u->debug=123456;
2215 #endif
2216  mpz_init(u->z);
2217  if (SR_HDL(b) & SR_INT)
2218  {
2219  number x=a;
2220  a=b;
2221  b=x;
2222  }
2223  if (SR_HDL(a) & SR_INT)
2224  {
2225  u->s=b->s;
2226  if (u->s==1) u->s=0;
2227  if (((long)a)>0L)
2228  {
2229  mpz_mul_ui(u->z,b->z,(unsigned long)SR_TO_INT(a));
2230  }
2231  else
2232  {
2233  if (a==INT_TO_SR(-1))
2234  {
2235  mpz_set(u->z,b->z);
2236  mpz_neg(u->z,u->z);
2237  u->s=b->s;
2238  }
2239  else
2240  {
2241  mpz_mul_ui(u->z,b->z,(unsigned long)-SR_TO_INT(a));
2242  mpz_neg(u->z,u->z);
2243  }
2244  }
2245  if (u->s<2)
2246  {
2247  if (mpz_cmp(u->z,b->n)==0)
2248  {
2249  mpz_clear(u->z);
2250  FREE_RNUMBER(u);
2251  return INT_TO_SR(1);
2252  }
2253  mpz_init_set(u->n,b->n);
2254  if (GCD_NORM_COND(b,u)) { nlNormalize_Gcd(u); }
2255  }
2256  else //u->s==3
2257  {
2258  u=nlShort3(u);
2259  }
2260  }
2261  else
2262  {
2263  mpz_mul(u->z,a->z,b->z);
2264  u->s = 0;
2265  if(a->s==3)
2266  {
2267  if(b->s==3)
2268  {
2269  u->s = 3;
2270  }
2271  else
2272  {
2273  if (mpz_cmp(u->z,b->n)==0)
2274  {
2275  mpz_clear(u->z);
2276  FREE_RNUMBER(u);
2277  return INT_TO_SR(1);
2278  }
2279  mpz_init_set(u->n,b->n);
2280  if (GCD_NORM_COND(b,u)) { nlNormalize_Gcd(u); }
2281  }
2282  }
2283  else
2284  {
2285  if(b->s==3)
2286  {
2287  if (mpz_cmp(u->z,a->n)==0)
2288  {
2289  mpz_clear(u->z);
2290  FREE_RNUMBER(u);
2291  return INT_TO_SR(1);
2292  }
2293  mpz_init_set(u->n,a->n);
2294  if (GCD_NORM_COND(a,u)) { nlNormalize_Gcd(u); }
2295  }
2296  else
2297  {
2298  mpz_init(u->n);
2299  mpz_mul(u->n,a->n,b->n);
2300  if (mpz_cmp(u->z,u->n)==0)
2301  {
2302  mpz_clear(u->z);
2303  mpz_clear(u->n);
2304  FREE_RNUMBER(u);
2305  return INT_TO_SR(1);
2306  }
2307  if (GCD_NORM_COND(a,u)) { nlNormalize_Gcd(u); }
2308  }
2309  }
2310  }
2311  return u;
2312 }
2313 
2314 /*2
2315 * copy a to b for mapping
2316 */
2317 number nlCopyMap(number a, const coeffs /*src*/, const coeffs /*dst*/)
2318 {
2319  if ((SR_HDL(a) & SR_INT)||(a==NULL))
2320  {
2321  return a;
2322  }
2323  return _nlCopy_NoImm(a);
2324 }
2325 
2326 nMapFunc nlSetMap(const coeffs src, const coeffs /*dst*/)
2327 {
2328  if (src->rep==n_rep_gap_rat) /*Q, coeffs_BIGINT */
2329  {
2330  return ndCopyMap;
2331  }
2332  if ((src->rep==n_rep_int) && nCoeff_is_Zp(src))
2333  {
2334  return nlMapP;
2335  }
2336  if ((src->rep==n_rep_float) && nCoeff_is_R(src))
2337  {
2338  return nlMapR;
2339  }
2340  if ((src->rep==n_rep_gmp_float) && nCoeff_is_long_R(src))
2341  {
2342  return nlMapLongR; /* long R -> Q */
2343  }
2344 #ifdef HAVE_RINGS
2345  if (src->rep==n_rep_gmp) // nCoeff_is_Ring_Z(src) || nCoeff_is_Ring_PtoM(src) || nCoeff_is_Ring_ModN(src))
2346  {
2347  return nlMapGMP;
2348  }
2349  if (src->rep==n_rep_gap_gmp)
2350  {
2351  return nlMapZ;
2352  }
2353  if ((src->rep==n_rep_int) && nCoeff_is_Ring_2toM(src))
2354  {
2355  return nlMapMachineInt;
2356  }
2357 #endif
2358  return NULL;
2359 }
2360 /*2
2361 * z := i
2362 */
2363 number nlRInit (long i)
2364 {
2365  number z=ALLOC_RNUMBER();
2366 #if defined(LDEBUG)
2367  z->debug=123456;
2368 #endif
2369  mpz_init_set_si(z->z,i);
2370  z->s = 3;
2371  return z;
2372 }
2373 
2374 /*2
2375 * z := i/j
2376 */
2377 number nlInit2 (int i, int j, const coeffs r)
2378 {
2379  number z=ALLOC_RNUMBER();
2380 #if defined(LDEBUG)
2381  z->debug=123456;
2382 #endif
2383  mpz_init_set_si(z->z,(long)i);
2384  mpz_init_set_si(z->n,(long)j);
2385  z->s = 0;
2386  nlNormalize(z,r);
2387  return z;
2388 }
2389 
2390 number nlInit2gmp (mpz_t i, mpz_t j, const coeffs r)
2391 {
2392  number z=ALLOC_RNUMBER();
2393 #if defined(LDEBUG)
2394  z->debug=123456;
2395 #endif
2396  mpz_init_set(z->z,i);
2397  mpz_init_set(z->n,j);
2398  z->s = 0;
2399  nlNormalize(z,r);
2400  return z;
2401 }
2402 
2403 #else // DO_LINLINE
2404 
2405 // declare immedate routines
2406 number nlRInit (long i);
2407 BOOLEAN _nlEqual_aNoImm_OR_bNoImm(number a, number b);
2408 number _nlCopy_NoImm(number a);
2409 number _nlNeg_NoImm(number a);
2410 number _nlAdd_aNoImm_OR_bNoImm(number a, number b);
2411 void _nlInpAdd_aNoImm_OR_bNoImm(number &a, number b);
2412 number _nlSub_aNoImm_OR_bNoImm(number a, number b);
2413 number _nlMult_aNoImm_OR_bNoImm(number a, number b);
2414 number _nlMult_aImm_bImm_rNoImm(number a, number b);
2415 
2416 #endif
2417 
2418 /***************************************************************
2419  *
2420  * Routines which might be inlined by p_Numbers.h
2421  *
2422  *******************************************************************/
2423 #if defined(DO_LINLINE) || !defined(P_NUMBERS_H)
2424 
2425 // routines which are always inlined/static
2426 
2427 /*2
2428 * a = b ?
2429 */
2430 LINLINE BOOLEAN nlEqual (number a, number b, const coeffs r)
2431 {
2432  nlTest(a, r);
2433  nlTest(b, r);
2434 // short - short
2435  if (SR_HDL(a) & SR_HDL(b) & SR_INT) return a==b;
2436  return _nlEqual_aNoImm_OR_bNoImm(a, b);
2437 }
2438 
2439 LINLINE number nlInit (long i, const coeffs r)
2440 {
2441  number n;
2442  #if MAX_NUM_SIZE == 60
2443  if (((i << 3) >> 3) == i) n=INT_TO_SR(i);
2444  else n=nlRInit(i);
2445  #else
2446  LONG ii=(LONG)i;
2447  if ( ((((long)ii)==i) && ((ii << 3) >> 3) == ii )) n=INT_TO_SR(ii);
2448  else n=nlRInit(i);
2449  #endif
2450  nlTest(n, r);
2451  return n;
2452 }
2453 
2454 /*2
2455 * a == 1 ?
2456 */
2457 LINLINE BOOLEAN nlIsOne (number a, const coeffs r)
2458 {
2459 #ifdef LDEBUG
2460  if (a==NULL) return FALSE;
2461  nlTest(a, r);
2462 #endif
2463  return (a==INT_TO_SR(1));
2464 }
2465 
2467 {
2468  #if 0
2469  if (a==INT_TO_SR(0)) return TRUE;
2470  if ((SR_HDL(a) & SR_INT)||(a==NULL)) return FALSE;
2471  if (mpz_cmp_si(a->z,0L)==0)
2472  {
2473  printf("gmp-0 in nlIsZero\n");
2474  dErrorBreak();
2475  return TRUE;
2476  }
2477  return FALSE;
2478  #else
2479  return (a==NULL)|| (a==INT_TO_SR(0));
2480  #endif
2481 }
2482 
2483 /*2
2484 * copy a to b
2485 */
2486 LINLINE number nlCopy(number a, const coeffs)
2487 {
2488  if ((SR_HDL(a) & SR_INT)||(a==NULL))
2489  {
2490  return a;
2491  }
2492  return _nlCopy_NoImm(a);
2493 }
2494 
2495 
2496 /*2
2497 * delete a
2498 */
2499 LINLINE void nlDelete (number * a, const coeffs r)
2500 {
2501  if (*a!=NULL)
2502  {
2503  nlTest(*a, r);
2504  if ((SR_HDL(*a) & SR_INT)==0)
2505  {
2506  _nlDelete_NoImm(a);
2507  }
2508  *a=NULL;
2509  }
2510 }
2511 
2512 /*2
2513 * za:= - za
2514 */
2515 LINLINE number nlNeg (number a, const coeffs R)
2516 {
2517  nlTest(a, R);
2518  if(SR_HDL(a) &SR_INT)
2519  {
2520  LONG r=SR_TO_INT(a);
2521  if (r==(-(POW_2_28))) a=nlRInit(POW_2_28);
2522  else a=INT_TO_SR(-r);
2523  return a;
2524  }
2525  a = _nlNeg_NoImm(a);
2526  nlTest(a, R);
2527  return a;
2528 
2529 }
2530 
2531 /*2
2532 * u:= a + b
2533 */
2534 LINLINE number nlAdd (number a, number b, const coeffs R)
2535 {
2536  if (SR_HDL(a) & SR_HDL(b) & SR_INT)
2537  {
2538  LONG r=SR_HDL(a)+SR_HDL(b)-1L;
2539  if ( ((r << 1) >> 1) == r )
2540  return (number)(long)r;
2541  else
2542  return nlRInit(SR_TO_INT(r));
2543  }
2544  number u = _nlAdd_aNoImm_OR_bNoImm(a, b);
2545  nlTest(u, R);
2546  return u;
2547 }
2548 
2549 number nlShort1(number a);
2550 number nlShort3_noinline(number x);
2551 
2552 LINLINE void nlInpAdd(number &a, number b, const coeffs r)
2553 {
2554  // a=a+b
2555  if (SR_HDL(a) & SR_HDL(b) & SR_INT)
2556  {
2557  LONG r=SR_HDL(a)+SR_HDL(b)-1L;
2558  if ( ((r << 1) >> 1) == r )
2559  a=(number)(long)r;
2560  else
2561  a=nlRInit(SR_TO_INT(r));
2562  }
2563  else
2564  {
2566  nlTest(a,r);
2567  }
2568 }
2569 
2570 LINLINE number nlMult (number a, number b, const coeffs R)
2571 {
2572  nlTest(a, R);
2573  nlTest(b, R);
2574  if (a==INT_TO_SR(0)) return INT_TO_SR(0);
2575  if (b==INT_TO_SR(0)) return INT_TO_SR(0);
2576  if (SR_HDL(a) & SR_HDL(b) & SR_INT)
2577  {
2578  LONG r=(LONG)((unsigned LONG)(SR_HDL(a)-1L))*((unsigned LONG)(SR_HDL(b)>>1));
2579  if ((r/(SR_HDL(b)>>1))==(SR_HDL(a)-1L))
2580  {
2581  number u=((number) ((r>>1)+SR_INT));
2582  if (((((LONG)SR_HDL(u))<<1)>>1)==SR_HDL(u)) return (u);
2583  return nlRInit(SR_HDL(u)>>2);
2584  }
2585  number u = _nlMult_aImm_bImm_rNoImm(a, b);
2586  nlTest(u, R);
2587  return u;
2588 
2589  }
2590  number u = _nlMult_aNoImm_OR_bNoImm(a, b);
2591  nlTest(u, R);
2592  return u;
2593 
2594 }
2595 
2596 
2597 /*2
2598 * u:= a - b
2599 */
2600 LINLINE number nlSub (number a, number b, const coeffs r)
2601 {
2602  if (SR_HDL(a) & SR_HDL(b) & SR_INT)
2603  {
2604  LONG r=SR_HDL(a)-SR_HDL(b)+1;
2605  if ( ((r << 1) >> 1) == r )
2606  {
2607  return (number)(long)r;
2608  }
2609  else
2610  return nlRInit(SR_TO_INT(r));
2611  }
2612  number u = _nlSub_aNoImm_OR_bNoImm(a, b);
2613  nlTest(u, r);
2614  return u;
2615 
2616 }
2617 
2618 LINLINE void nlInpMult(number &a, number b, const coeffs r)
2619 {
2620  number aa=a;
2621  if (((SR_HDL(b)|SR_HDL(aa))&SR_INT))
2622  {
2623  number n=nlMult(aa,b,r);
2624  nlDelete(&a,r);
2625  a=n;
2626  }
2627  else
2628  {
2629  mpz_mul(aa->z,a->z,b->z);
2630  if (aa->s==3)
2631  {
2632  if(b->s!=3)
2633  {
2634  mpz_init_set(a->n,b->n);
2635  a->s=0;
2636  }
2637  }
2638  else
2639  {
2640  if(b->s!=3)
2641  {
2642  mpz_mul(a->n,a->n,b->n);
2643  }
2644  a->s=0;
2645  }
2646  }
2647 }
2648 #endif // DO_LINLINE
2649 
2650 #ifndef P_NUMBERS_H
2651 
2652 static void nlMPZ(mpz_t m, number &n, const coeffs r)
2653 {
2654  nlTest(n, r);
2655  nlNormalize(n, r);
2656  if (SR_HDL(n) & SR_INT) mpz_init_set_si(m, SR_TO_INT(n)); /* n fits in an int */
2657  else mpz_init_set(m, (mpz_ptr)n->z);
2658 }
2659 
2660 
2661 static number nlInitMPZ(mpz_t m, const coeffs)
2662 {
2663  number z = ALLOC_RNUMBER();
2664  z->s = 3;
2665  #ifdef LDEBUG
2666  z->debug=123456;
2667  #endif
2668  mpz_init_set(z->z, m);
2669  z=nlShort3(z);
2670  return z;
2671 }
2672 
2673 number nlXExtGcd (number a, number b, number *s, number *t, number *u, number *v, const coeffs r)
2674 {
2675  if (SR_HDL(a) & SR_HDL(b) & SR_INT)
2676  {
2677  int uu, vv, x, y;
2678  int g = int_extgcd(SR_TO_INT(a), SR_TO_INT(b), &uu, &vv, &x, &y);
2679  *s = INT_TO_SR(uu);
2680  *t = INT_TO_SR(vv);
2681  *u = INT_TO_SR(x);
2682  *v = INT_TO_SR(y);
2683  return INT_TO_SR(g);
2684  }
2685  else
2686  {
2687  mpz_t aa, bb;
2688  if (SR_HDL(a) & SR_INT)
2689  {
2690  mpz_init_set_si(aa, SR_TO_INT(a));
2691  }
2692  else
2693  {
2694  mpz_init_set(aa, a->z);
2695  }
2696  if (SR_HDL(b) & SR_INT)
2697  {
2698  mpz_init_set_si(bb, SR_TO_INT(b));
2699  }
2700  else
2701  {
2702  mpz_init_set(bb, b->z);
2703  }
2704  mpz_t erg; mpz_t bs; mpz_t bt;
2705  mpz_init(erg);
2706  mpz_init(bs);
2707  mpz_init(bt);
2708 
2709  mpz_gcdext(erg, bs, bt, aa, bb);
2710 
2711  mpz_div(aa, aa, erg);
2712  *u=nlInitMPZ(bb,r);
2713  *u=nlNeg(*u,r);
2714  *v=nlInitMPZ(aa,r);
2715 
2716  mpz_clear(aa);
2717  mpz_clear(bb);
2718 
2719  *s = nlInitMPZ(bs,r);
2720  *t = nlInitMPZ(bt,r);
2721  return nlInitMPZ(erg,r);
2722  }
2723 }
2724 
2725 number nlQuotRem (number a, number b, number * r, const coeffs R)
2726 {
2727  assume(SR_TO_INT(b)!=0);
2728  if (SR_HDL(a) & SR_HDL(b) & SR_INT)
2729  {
2730  if (r!=NULL)
2731  *r = INT_TO_SR(SR_TO_INT(a) % SR_TO_INT(b));
2732  return INT_TO_SR(SR_TO_INT(a)/SR_TO_INT(b));
2733  }
2734  else if (SR_HDL(a) & SR_INT)
2735  {
2736  // -2^xx / 2^xx
2737  if ((a==INT_TO_SR(-(POW_2_28)))&&(b==INT_TO_SR(-1L)))
2738  {
2739  if (r!=NULL) *r=INT_TO_SR(0);
2740  return nlRInit(POW_2_28);
2741  }
2742  //a is small, b is not, so q=0, r=a
2743  if (r!=NULL)
2744  *r = a;
2745  return INT_TO_SR(0);
2746  }
2747  else if (SR_HDL(b) & SR_INT)
2748  {
2749  unsigned long rr;
2750  mpz_t qq;
2751  mpz_init(qq);
2752  mpz_t rrr;
2753  mpz_init(rrr);
2754  rr = mpz_divmod_ui(qq, rrr, a->z, (unsigned long)ABS(SR_TO_INT(b)));
2755  mpz_clear(rrr);
2756 
2757  if (r!=NULL)
2758  *r = INT_TO_SR(rr);
2759  if (SR_TO_INT(b)<0)
2760  {
2761  mpz_neg(qq, qq);
2762  }
2763  return nlInitMPZ(qq,R);
2764  }
2765  mpz_t qq,rr;
2766  mpz_init(qq);
2767  mpz_init(rr);
2768  mpz_divmod(qq, rr, a->z, b->z);
2769  if (r!=NULL)
2770  *r = nlInitMPZ(rr,R);
2771  else
2772  {
2773  mpz_clear(rr);
2774  }
2775  return nlInitMPZ(qq,R);
2776 }
2777 
2778 void nlInpGcd(number &a, number b, const coeffs r)
2779 {
2780  if ((SR_HDL(b)|SR_HDL(a))&SR_INT)
2781  {
2782  number n=nlGcd(a,b,r);
2783  nlDelete(&a,r);
2784  a=n;
2785  }
2786  else
2787  {
2788  mpz_gcd(a->z,a->z,b->z);
2790  }
2791 }
2792 
2793 void nlInpIntDiv(number &a, number b, const coeffs r)
2794 {
2795  if ((SR_HDL(b)|SR_HDL(a))&SR_INT)
2796  {
2797  number n=nlIntDiv(a,b, r);
2798  nlDelete(&a,r);
2799  a=n;
2800  }
2801  else
2802  {
2803  number rr=nlIntMod(a,b,r);
2804  if (SR_HDL(rr) & SR_INT) mpz_sub_ui(a->z,a->z,SR_TO_INT(rr));
2805  else mpz_sub(a->z,a->z,rr->z);
2806  mpz_divexact(a->z,a->z,b->z);
2808  }
2809 }
2810 
2811 number nlFarey(number nN, number nP, const coeffs r)
2812 {
2813  mpz_t tmp; mpz_init(tmp);
2814  mpz_t A,B,C,D,E,N,P;
2815  if (SR_HDL(nN) & SR_INT) mpz_init_set_si(N,SR_TO_INT(nN));
2816  else mpz_init_set(N,nN->z);
2817  if (SR_HDL(nP) & SR_INT) mpz_init_set_si(P,SR_TO_INT(nP));
2818  else mpz_init_set(P,nP->z);
2819  assume(!mpz_isNeg(P));
2820  if (mpz_isNeg(N)) mpz_add(N,N,P);
2821  mpz_init_set_si(A,0L);
2822  mpz_init_set_ui(B,(unsigned long)1);
2823  mpz_init_set_si(C,0L);
2824  mpz_init(D);
2825  mpz_init_set(E,P);
2826  number z=INT_TO_SR(0);
2827  while(mpz_cmp_si(N,0L)!=0)
2828  {
2829  mpz_mul(tmp,N,N);
2830  mpz_add(tmp,tmp,tmp);
2831  if (mpz_cmp(tmp,P)<0)
2832  {
2833  if (mpz_isNeg(B))
2834  {
2835  mpz_neg(B,B);
2836  mpz_neg(N,N);
2837  }
2838  // check for gcd(N,B)==1
2839  mpz_gcd(tmp,N,B);
2840  if (mpz_cmp_ui(tmp,1)==0)
2841  {
2842  // return N/B
2843  z=ALLOC_RNUMBER();
2844  #ifdef LDEBUG
2845  z->debug=123456;
2846  #endif
2847  mpz_init_set(z->z,N);
2848  mpz_init_set(z->n,B);
2849  z->s = 0;
2850  nlNormalize(z,r);
2851  }
2852  else
2853  {
2854  // return nN (the input) instead of "fail"
2855  z=nlCopy(nN,r);
2856  }
2857  break;
2858  }
2859  //mpz_mod(D,E,N);
2860  //mpz_div(tmp,E,N);
2861  mpz_divmod(tmp,D,E,N);
2862  mpz_mul(tmp,tmp,B);
2863  mpz_sub(C,A,tmp);
2864  mpz_set(E,N);
2865  mpz_set(N,D);
2866  mpz_set(A,B);
2867  mpz_set(B,C);
2868  }
2869  mpz_clear(tmp);
2870  mpz_clear(A);
2871  mpz_clear(B);
2872  mpz_clear(C);
2873  mpz_clear(D);
2874  mpz_clear(E);
2875  mpz_clear(N);
2876  mpz_clear(P);
2877  return z;
2878 }
2879 
2880 number nlExtGcd(number a, number b, number *s, number *t, const coeffs)
2881 {
2882  mpz_ptr aa,bb;
2883  *s=ALLOC_RNUMBER();
2884  mpz_init((*s)->z); (*s)->s=3;
2885  (*t)=ALLOC_RNUMBER();
2886  mpz_init((*t)->z); (*t)->s=3;
2887  number g=ALLOC_RNUMBER();
2888  mpz_init(g->z); g->s=3;
2889  #ifdef LDEBUG
2890  g->debug=123456;
2891  (*s)->debug=123456;
2892  (*t)->debug=123456;
2893  #endif
2894  if (SR_HDL(a) & SR_INT)
2895  {
2896  aa=(mpz_ptr)omAlloc(sizeof(mpz_t));
2897  mpz_init_set_si(aa,SR_TO_INT(a));
2898  }
2899  else
2900  {
2901  aa=a->z;
2902  }
2903  if (SR_HDL(b) & SR_INT)
2904  {
2905  bb=(mpz_ptr)omAlloc(sizeof(mpz_t));
2906  mpz_init_set_si(bb,SR_TO_INT(b));
2907  }
2908  else
2909  {
2910  bb=b->z;
2911  }
2912  mpz_gcdext(g->z,(*s)->z,(*t)->z,aa,bb);
2913  g=nlShort3(g);
2914  (*s)=nlShort3((*s));
2915  (*t)=nlShort3((*t));
2916  if (SR_HDL(a) & SR_INT)
2917  {
2918  mpz_clear(aa);
2919  omFreeSize(aa, sizeof(mpz_t));
2920  }
2921  if (SR_HDL(b) & SR_INT)
2922  {
2923  mpz_clear(bb);
2924  omFreeSize(bb, sizeof(mpz_t));
2925  }
2926  return g;
2927 }
2928 
2929 void nlCoeffWrite (const coeffs r, BOOLEAN /*details*/)
2930 {
2931  if (r->is_field)
2932  PrintS("QQ");
2933  else
2934  PrintS("ZZ");
2935 }
2936 
2938 number nlChineseRemainderSym(number *x, number *q,int rl, BOOLEAN sym, CFArray &inv_cache,const coeffs CF)
2939 // elemenst in the array are x[0..(rl-1)], q[0..(rl-1)]
2940 {
2941  setCharacteristic( 0 ); // only in char 0
2942  Off(SW_RATIONAL);
2943  CFArray X(rl), Q(rl);
2944  int i;
2945  for(i=rl-1;i>=0;i--)
2946  {
2947  X[i]=CF->convSingNFactoryN(x[i],FALSE,CF); // may be larger MAX_INT
2948  Q[i]=CF->convSingNFactoryN(q[i],FALSE,CF); // may be larger MAX_INT
2949  }
2950  CanonicalForm xnew,qnew;
2951  if (n_SwitchChinRem)
2952  chineseRemainder(X,Q,xnew,qnew);
2953  else
2954  chineseRemainderCached(X,Q,xnew,qnew,inv_cache);
2955  number n=CF->convFactoryNSingN(xnew,CF);
2956  if (sym)
2957  {
2958  number p=CF->convFactoryNSingN(qnew,CF);
2959  number p2;
2960  if (getCoeffType(CF) == n_Q) p2=nlIntDiv(p,nlInit(2, CF),CF);
2961  else p2=CF->cfDiv(p,CF->cfInit(2, CF),CF);
2962  if (CF->cfGreater(n,p2,CF))
2963  {
2964  number n2=CF->cfSub(n,p,CF);
2965  CF->cfDelete(&n,CF);
2966  n=n2;
2967  }
2968  CF->cfDelete(&p2,CF);
2969  CF->cfDelete(&p,CF);
2970  }
2971  CF->cfNormalize(n,CF);
2972  return n;
2973 }
2974 #if 0
2975 number nlChineseRemainder(number *x, number *q,int rl, const coeffs C)
2976 {
2977  CFArray inv(rl);
2978  return nlChineseRemainderSym(x,q,rl,TRUE,inv,C);
2979 }
2980 #endif
2981 
2982 static void nlClearContent(ICoeffsEnumerator& numberCollectionEnumerator, number& c, const coeffs cf)
2983 {
2984  assume(cf != NULL);
2985 
2986  numberCollectionEnumerator.Reset();
2987 
2988  if( !numberCollectionEnumerator.MoveNext() ) // empty zero polynomial?
2989  {
2990  c = nlInit(1, cf);
2991  return;
2992  }
2993 
2994  // all coeffs are given by integers!!!
2995 
2996  // part 1, find a small candidate for gcd
2997  number cand1,cand;
2998  int s1,s;
2999  s=2147483647; // max. int
3000 
3001  const BOOLEAN lc_is_pos=nlGreaterZero(numberCollectionEnumerator.Current(),cf);
3002 
3003  int normalcount = 0;
3004  do
3005  {
3006  number& n = numberCollectionEnumerator.Current();
3007  nlNormalize(n, cf); ++normalcount;
3008  cand1 = n;
3009 
3010  if (SR_HDL(cand1)&SR_INT) { cand=cand1; break; }
3011  assume(cand1->s==3); // all coeffs should be integers // ==0?!! after printing
3012  s1=mpz_size1(cand1->z);
3013  if (s>s1)
3014  {
3015  cand=cand1;
3016  s=s1;
3017  }
3018  } while (numberCollectionEnumerator.MoveNext() );
3019 
3020 // assume( nlGreaterZero(cand,cf) ); // cand may be a negative integer!
3021 
3022  cand=nlCopy(cand,cf);
3023  // part 2: compute gcd(cand,all coeffs)
3024 
3025  numberCollectionEnumerator.Reset();
3026 
3027  while (numberCollectionEnumerator.MoveNext() )
3028  {
3029  number& n = numberCollectionEnumerator.Current();
3030 
3031  if( (--normalcount) <= 0)
3032  nlNormalize(n, cf);
3033 
3034  nlInpGcd(cand, n, cf);
3036 
3037  if(nlIsOne(cand,cf))
3038  {
3039  c = cand;
3040 
3041  if(!lc_is_pos)
3042  {
3043  // make the leading coeff positive
3044  c = nlNeg(c, cf);
3045  numberCollectionEnumerator.Reset();
3046 
3047  while (numberCollectionEnumerator.MoveNext() )
3048  {
3049  number& nn = numberCollectionEnumerator.Current();
3050  nn = nlNeg(nn, cf);
3051  }
3052  }
3053  return;
3054  }
3055  }
3056 
3057  // part3: all coeffs = all coeffs / cand
3058  if (!lc_is_pos)
3059  cand = nlNeg(cand,cf);
3060 
3061  c = cand;
3062  numberCollectionEnumerator.Reset();
3063 
3064  while (numberCollectionEnumerator.MoveNext() )
3065  {
3066  number& n = numberCollectionEnumerator.Current();
3067  number t=nlIntDiv(n, cand, cf); // simple integer exact division, no ratios to remain
3068  nlDelete(&n, cf);
3069  n = t;
3070  }
3071 }
3072 
3073 static void nlClearDenominators(ICoeffsEnumerator& numberCollectionEnumerator, number& c, const coeffs cf)
3074 {
3075  assume(cf != NULL);
3076 
3077  numberCollectionEnumerator.Reset();
3078 
3079  if( !numberCollectionEnumerator.MoveNext() ) // empty zero polynomial?
3080  {
3081  c = nlInit(1, cf);
3082 // assume( n_GreaterZero(c, cf) );
3083  return;
3084  }
3085 
3086  // all coeffs are given by integers after returning from this routine
3087 
3088  // part 1, collect product of all denominators /gcds
3089  number cand;
3090  cand=ALLOC_RNUMBER();
3091 #if defined(LDEBUG)
3092  cand->debug=123456;
3093 #endif
3094  cand->s=3;
3095 
3096  int s=0;
3097 
3098  const BOOLEAN lc_is_pos=nlGreaterZero(numberCollectionEnumerator.Current(),cf);
3099 
3100  do
3101  {
3102  number& cand1 = numberCollectionEnumerator.Current();
3103 
3104  if (!(SR_HDL(cand1)&SR_INT))
3105  {
3106  nlNormalize(cand1, cf);
3107  if ((!(SR_HDL(cand1)&SR_INT)) // not a short int
3108  && (cand1->s==1)) // and is a normalised rational
3109  {
3110  if (s==0) // first denom, we meet
3111  {
3112  mpz_init_set(cand->z, cand1->n); // cand->z = cand1->n
3113  s=1;
3114  }
3115  else // we have already something
3116  {
3117  mpz_lcm(cand->z, cand->z, cand1->n);
3118  }
3119  }
3120  }
3121  }
3122  while (numberCollectionEnumerator.MoveNext() );
3123 
3124 
3125  if (s==0) // nothing to do, all coeffs are already integers
3126  {
3127 // mpz_clear(tmp);
3128  FREE_RNUMBER(cand);
3129  if (lc_is_pos)
3130  c=nlInit(1,cf);
3131  else
3132  {
3133  // make the leading coeff positive
3134  c=nlInit(-1,cf);
3135 
3136  // TODO: incorporate the following into the loop below?
3137  numberCollectionEnumerator.Reset();
3138  while (numberCollectionEnumerator.MoveNext() )
3139  {
3140  number& n = numberCollectionEnumerator.Current();
3141  n = nlNeg(n, cf);
3142  }
3143  }
3144 // assume( n_GreaterZero(c, cf) );
3145  return;
3146  }
3147 
3148  cand = nlShort3(cand);
3149 
3150  // part2: all coeffs = all coeffs * cand
3151  // make the lead coeff positive
3152  numberCollectionEnumerator.Reset();
3153 
3154  if (!lc_is_pos)
3155  cand = nlNeg(cand, cf);
3156 
3157  c = cand;
3158 
3159  while (numberCollectionEnumerator.MoveNext() )
3160  {
3161  number &n = numberCollectionEnumerator.Current();
3162  nlInpMult(n, cand, cf);
3163  }
3164 
3165 }
3166 
3167 char * nlCoeffName(const coeffs r)
3168 {
3169  if (r->cfDiv==nlDiv) return (char*)"QQ";
3170  else return (char*)"ZZ";
3171 }
3172 
3173 static char* nlCoeffString(const coeffs r)
3174 {
3175  //return omStrDup(nlCoeffName(r));
3176  if (r->cfDiv==nlDiv) return omStrDup("QQ");
3177  else return omStrDup("ZZ");
3178 }
3179 
3180 static void nlWriteFd(number n,FILE* f, const coeffs)
3181 {
3182  if(SR_HDL(n) & SR_INT)
3183  {
3184  #if SIZEOF_LONG == 4
3185  fprintf(f,"4 %ld ",SR_TO_INT(n));
3186  #else
3187  long nn=SR_TO_INT(n);
3188  if ((nn<POW_2_28_32)&&(nn>= -POW_2_28_32))
3189  {
3190  int nnn=(int)nn;
3191  fprintf(f,"4 %d ",nnn);
3192  }
3193  else
3194  {
3195  mpz_t tmp;
3196  mpz_init_set_si(tmp,nn);
3197  fputs("8 ",f);
3198  mpz_out_str (f,SSI_BASE, tmp);
3199  fputc(' ',f);
3200  mpz_clear(tmp);
3201  }
3202  #endif
3203  }
3204  else if (n->s<2)
3205  {
3206  //gmp_fprintf(f,"%d %Zd %Zd ",n->s,n->z,n->n);
3207  fprintf(f,"%d ",n->s+5);
3208  mpz_out_str (f,SSI_BASE, n->z);
3209  fputc(' ',f);
3210  mpz_out_str (f,SSI_BASE, n->n);
3211  fputc(' ',f);
3212 
3213  //if (d->f_debug!=NULL) gmp_fprintf(d->f_debug,"number: s=%d gmp/gmp \"%Zd %Zd\" ",n->s,n->z,n->n);
3214  }
3215  else /*n->s==3*/
3216  {
3217  //gmp_fprintf(d->f_write,"3 %Zd ",n->z);
3218  fputs("8 ",f);
3219  mpz_out_str (f,SSI_BASE, n->z);
3220  fputc(' ',f);
3221 
3222  //if (d->f_debug!=NULL) gmp_fprintf(d->f_debug,"number: gmp \"%Zd\" ",n->z);
3223  }
3224 }
3225 
3226 static number nlReadFd(s_buff f, const coeffs)
3227 {
3228  int sub_type=-1;
3229  sub_type=s_readint(f);
3230  switch(sub_type)
3231  {
3232  case 0:
3233  case 1:
3234  {// read mpz_t, mpz_t
3235  number n=nlRInit(0);
3236  mpz_init(n->n);
3237  s_readmpz(f,n->z);
3238  s_readmpz(f,n->n);
3239  n->s=sub_type;
3240  return n;
3241  }
3242 
3243  case 3:
3244  {// read mpz_t
3245  number n=nlRInit(0);
3246  s_readmpz(f,n->z);
3247  n->s=3; /*sub_type*/
3248  #if SIZEOF_LONG == 8
3249  n=nlShort3(n);
3250  #endif
3251  return n;
3252  }
3253  case 4:
3254  {
3255  LONG dd=s_readlong(f);
3256  //#if SIZEOF_LONG == 8
3257  return INT_TO_SR(dd);
3258  //#else
3259  //return nlInit(dd,NULL);
3260  //#endif
3261  }
3262  case 5:
3263  case 6:
3264  {// read raw mpz_t, mpz_t
3265  number n=nlRInit(0);
3266  mpz_init(n->n);
3267  s_readmpz_base (f,n->z, SSI_BASE);
3268  s_readmpz_base (f,n->n, SSI_BASE);
3269  n->s=sub_type-5;
3270  return n;
3271  }
3272  case 8:
3273  {// read raw mpz_t
3274  number n=nlRInit(0);
3275  s_readmpz_base (f,n->z, SSI_BASE);
3276  n->s=sub_type=3; /*subtype-5*/
3277  #if SIZEOF_LONG == 8
3278  n=nlShort3(n);
3279  #endif
3280  return n;
3281  }
3282 
3283  default: Werror("error in reading number: invalid subtype %d",sub_type);
3284  return NULL;
3285  }
3286  return NULL;
3287 }
3289 {
3290  /* test, if r is an instance of nInitCoeffs(n,parameter) */
3291  /* if parameter is not needed */
3292  if (n==r->type)
3293  {
3294  if ((p==NULL)&&(r->cfDiv==nlDiv)) return TRUE;
3295  if ((p!=NULL)&&(r->cfDiv!=nlDiv)) return TRUE;
3296  }
3297  return FALSE;
3298 }
3299 
3300 static number nlLcm(number a,number b,const coeffs r)
3301 {
3302  number g=nlGcd(a,b,r);
3303  number n1=nlMult(a,b,r);
3304  number n2=nlIntDiv(n1,g,r);
3305  nlDelete(&g,r);
3306  nlDelete(&n1,r);
3307  return n2;
3308 }
3309 
3310 static number nlRandom(siRandProc p, number v2, number, const coeffs cf)
3311 {
3312  number a=nlInit(p(),cf);
3313  if (v2!=NULL)
3314  {
3315  number b=nlInit(p(),cf);
3316  number c=nlDiv(a,b,cf);
3317  nlDelete(&b,cf);
3318  nlDelete(&a,cf);
3319  a=c;
3320  }
3321  return a;
3322 }
3323 
3325 {
3326  r->is_domain=TRUE;
3327  r->rep=n_rep_gap_rat;
3328 
3329  r->nCoeffIsEqual=nlCoeffIsEqual;
3330  //r->cfKillChar = ndKillChar; /* dummy */
3331  r->cfCoeffString=nlCoeffString;
3332  r->cfCoeffName=nlCoeffName;
3333 
3334  r->cfInitMPZ = nlInitMPZ;
3335  r->cfMPZ = nlMPZ;
3336 
3337  r->cfMult = nlMult;
3338  r->cfSub = nlSub;
3339  r->cfAdd = nlAdd;
3340  r->cfExactDiv= nlExactDiv;
3341  if (p==NULL) /* Q */
3342  {
3343  r->is_field=TRUE;
3344  r->cfDiv = nlDiv;
3345  //r->cfGcd = ndGcd_dummy;
3346  r->cfSubringGcd = nlGcd;
3347  }
3348  else /* Z: coeffs_BIGINT */
3349  {
3350  r->is_field=FALSE;
3351  r->cfDiv = nlIntDiv;
3352  r->cfIntMod= nlIntMod;
3353  r->cfGcd = nlGcd;
3354  r->cfDivBy=nlDivBy;
3355  r->cfDivComp = nlDivComp;
3356  r->cfIsUnit = nlIsUnit;
3357  r->cfGetUnit = nlGetUnit;
3358  r->cfQuot1 = nlQuot1;
3359  r->cfLcm = nlLcm;
3360  r->cfXExtGcd=nlXExtGcd;
3361  r->cfQuotRem=nlQuotRem;
3362  }
3363  r->cfInit = nlInit;
3364  r->cfSize = nlSize;
3365  r->cfInt = nlInt;
3366 
3367  r->cfChineseRemainder=nlChineseRemainderSym;
3368  r->cfFarey=nlFarey;
3369  r->cfInpNeg = nlNeg;
3370  r->cfInvers= nlInvers;
3371  r->cfCopy = nlCopy;
3372  r->cfRePart = nlCopy;
3373  //r->cfImPart = ndReturn0;
3374  r->cfWriteLong = nlWrite;
3375  r->cfRead = nlRead;
3376  r->cfNormalize=nlNormalize;
3377  r->cfGreater = nlGreater;
3378  r->cfEqual = nlEqual;
3379  r->cfIsZero = nlIsZero;
3380  r->cfIsOne = nlIsOne;
3381  r->cfIsMOne = nlIsMOne;
3382  r->cfGreaterZero = nlGreaterZero;
3383  r->cfPower = nlPower;
3384  r->cfGetDenom = nlGetDenom;
3385  r->cfGetNumerator = nlGetNumerator;
3386  r->cfExtGcd = nlExtGcd; // only for ring stuff and Z
3387  r->cfNormalizeHelper = nlNormalizeHelper;
3388  r->cfDelete= nlDelete;
3389  r->cfSetMap = nlSetMap;
3390  //r->cfName = ndName;
3391  r->cfInpMult=nlInpMult;
3392  r->cfInpAdd=nlInpAdd;
3393  r->cfCoeffWrite=nlCoeffWrite;
3394 
3395  r->cfClearContent = nlClearContent;
3396  r->cfClearDenominators = nlClearDenominators;
3397 
3398 #ifdef LDEBUG
3399  // debug stuff
3400  r->cfDBTest=nlDBTest;
3401 #endif
3402  r->convSingNFactoryN=nlConvSingNFactoryN;
3403  r->convFactoryNSingN=nlConvFactoryNSingN;
3404 
3405  r->cfRandom=nlRandom;
3406 
3407  // io via ssi
3408  r->cfWriteFd=nlWriteFd;
3409  r->cfReadFd=nlReadFd;
3410 
3411  // the variables: general stuff (required)
3412  r->nNULL = INT_TO_SR(0);
3413  //r->type = n_Q;
3414  r->ch = 0;
3415  r->has_simple_Alloc=FALSE;
3416  r->has_simple_Inverse=FALSE;
3417 
3418  // variables for this type of coeffs:
3419  // (none)
3420  return FALSE;
3421 }
3422 #if 0
3423 number nlMod(number a, number b)
3424 {
3425  if (((SR_HDL(b)&SR_HDL(a))&SR_INT)
3426  {
3427  int bi=SR_TO_INT(b);
3428  int ai=SR_TO_INT(a);
3429  int bb=ABS(bi);
3430  int c=ai%bb;
3431  if (c<0) c+=bb;
3432  return (INT_TO_SR(c));
3433  }
3434  number al;
3435  number bl;
3436  if (SR_HDL(a))&SR_INT)
3437  al=nlRInit(SR_TO_INT(a));
3438  else
3439  al=nlCopy(a);
3440  if (SR_HDL(b))&SR_INT)
3441  bl=nlRInit(SR_TO_INT(b));
3442  else
3443  bl=nlCopy(b);
3444  number r=nlRInit(0);
3445  mpz_mod(r->z,al->z,bl->z);
3446  nlDelete(&al);
3447  nlDelete(&bl);
3448  if (mpz_size1(&r->z)<=MP_SMALL)
3449  {
3450  LONG ui=(int)mpz_get_si(&r->z);
3451  if ((((ui<<3)>>3)==ui)
3452  && (mpz_cmp_si(x->z,(long)ui)==0))
3453  {
3454  mpz_clear(&r->z);
3455  FREE_RNUMBER(r); // omFreeBin((void *)r, rnumber_bin);
3456  r=INT_TO_SR(ui);
3457  }
3458  }
3459  return r;
3460 }
3461 #endif
3462 #endif // not P_NUMBERS_H
3463 #endif // LONGRAT_CC
mpz_t z
Definition: longrat.h:51
LINLINE number nlSub(number la, number li, const coeffs r)
Definition: longrat.cc:2600
static void nlClearDenominators(ICoeffsEnumerator &numberCollectionEnumerator, number &c, const coeffs cf)
Definition: longrat.cc:3073
const CanonicalForm int s
Definition: facAbsFact.cc:55
const CanonicalForm int const CFList const Variable & y
Definition: facAbsFact.cc:57
void mpz_mul_si(mpz_ptr r, mpz_srcptr s, long int si)
Definition: longrat.cc:176
#define omCheckAddrSize(addr, size)
Definition: omAllocDecl.h:327
#define D(A)
Definition: gentable.cc:123
#define INT_TO_SR(INT)
Definition: longrat.h:69
const poly a
Definition: syzextra.cc:212
BOOLEAN nlCoeffIsEqual(const coeffs r, n_coeffType n, void *p)
Definition: longrat.cc:3288
#define Print
Definition: emacs.cc:83
only used if HAVE_RINGS is defined
Definition: coeffs.h:44
static FORCE_INLINE BOOLEAN nCoeff_is_Zp(const coeffs r)
Definition: coeffs.h:834
static int int_extgcd(int a, int b, int *u, int *x, int *v, int *y)
Definition: longrat.cc:1278
char * nlCoeffName(const coeffs r)
Definition: longrat.cc:3167
void Off(int sw)
switches
CanonicalForm num(const CanonicalForm &f)
long npInt(number &n, const coeffs r)
Definition: modulop.cc:117
Definition: int_poly.h:33
static number nlConvFactoryNSingN(const CanonicalForm f, const coeffs r)
Definition: longrat.cc:374
BOOLEAN nlGreaterZero(number za, const coeffs r)
Definition: longrat.cc:1170
number nlModP(number q, const coeffs, const coeffs Zp)
Definition: longrat.cc:1440
#define FALSE
Definition: auxiliary.h:94
static void nlMPZ(mpz_t m, number &n, const coeffs r)
Definition: longrat.cc:2652
mpf_t * _mpfp()
Definition: mpr_complex.h:134
return P p
Definition: myNF.cc:203
number _nlMult_aNoImm_OR_bNoImm(number a, number b)
Definition: longrat.cc:2209
number nlShort1(number x)
Definition: longrat.cc:1328
number nlNormalizeHelper(number a, number b, const coeffs r)
Definition: longrat.cc:1393
number ndCopyMap(number a, const coeffs aRing, const coeffs r)
Definition: numbers.cc:244
static FORCE_INLINE BOOLEAN nCoeff_is_long_R(const coeffs r)
Definition: coeffs.h:908
LINLINE void nlInpAdd(number &a, number b, const coeffs r)
Definition: longrat.cc:2552
number nlGetDenom(number &n, const coeffs r)
Definition: longrat.cc:1503
void nlWrite(number a, const coeffs r)
Definition: longrat0.cc:113
int nlSize(number a, const coeffs)
Definition: longrat.cc:574
rational (GMP) numbers
Definition: coeffs.h:31
int n_SwitchChinRem
Definition: longrat.cc:2937
static FORCE_INLINE number n_Init(long i, const coeffs r)
a number representing i in the given coeff field/ring r
Definition: coeffs.h:542
static FORCE_INLINE BOOLEAN nCoeff_is_R(const coeffs r)
Definition: coeffs.h:853
#define omCheckIf(cond, test)
Definition: omAllocDecl.h:323
#define omFreeSize(addr, size)
Definition: omAllocDecl.h:260
LINLINE number nlAdd(number la, number li, const coeffs r)
Definition: longrat.cc:2534
{p < 2^31}
Definition: coeffs.h:30
void nlInpGcd(number &a, number b, const coeffs r)
Definition: longrat.cc:2778
BOOLEAN nlIsMOne(number a, const coeffs r)
Definition: longrat.cc:1195
static FORCE_INLINE BOOLEAN nCoeff_is_Ring_2toM(const coeffs r)
Definition: coeffs.h:750
(), see rinteger.h, new impl.
Definition: coeffs.h:112
void nlCoeffWrite(const coeffs r, BOOLEAN details)
Definition: longrat.cc:2929
number nlIntDiv(number a, number b, const coeffs r)
Definition: longrat.cc:800
number nlGetUnit(number n, const coeffs cf)
Definition: longrat.cc:967
static FORCE_INLINE int n_GetChar(const coeffs r)
Return the characteristic of the coeff. domain.
Definition: coeffs.h:448
number nlGcd(number a, number b, const coeffs r)
Definition: longrat.cc:1207
factory&#39;s main class
Definition: canonicalform.h:75
#define TRUE
Definition: auxiliary.h:98
coeffs nlQuot1(number c, const coeffs r)
Definition: longrat.cc:973
#define POW_2_28
Definition: longrat.cc:103
number nlRInit(long i)
Definition: longrat.cc:2363
#define FREE_RNUMBER(x)
Definition: coeffs.h:86
number nlInit2(int i, int j, const coeffs r)
create a rational i/j (implicitly) over Q NOTE: make sure to use correct Q in debug mode ...
Definition: longrat.cc:2377
g
Definition: cfModGcd.cc:4031
const char * nlRead(const char *s, number *a, const coeffs r)
Definition: longrat0.cc:54
void WerrorS(const char *s)
Definition: feFopen.cc:24
bool negative(N n)
Definition: ValueTraits.h:119
void s_readmpz_base(s_buff F, mpz_ptr a, int base)
Definition: s_buff.cc:207
CanonicalForm make_cf(const mpz_ptr n)
Definition: singext.cc:70
#define Q
Definition: sirandom.c:25
number nlIntMod(number a, number b, const coeffs r)
Definition: longrat.cc:881
#define POW_2_28_32
Definition: longrat.cc:104
number nlInit2gmp(mpz_t i, mpz_t j, const coeffs r)
create a rational i/j (implicitly) over Q NOTE: make sure to use correct Q in debug mode ...
Definition: longrat.cc:2390
#define WarnS
Definition: emacs.cc:81
BOOLEAN nlInitChar(coeffs r, void *p)
Definition: longrat.cc:3324
#define omAlloc(size)
Definition: omAllocDecl.h:210
void setCharacteristic(int c)
Definition: cf_char.cc:23
BOOLEAN nlGreater(number a, number b, const coeffs r)
Definition: longrat.cc:1180
LINLINE number nl_Copy(number a, const coeffs r)
static number nlInitMPZ(mpz_t m, const coeffs)
Definition: longrat.cc:2661
real floating point (GMP) numbers
Definition: coeffs.h:34
number nlMapZ(number from, const coeffs src, const coeffs dst)
Definition: longrat.cc:217
LINLINE BOOLEAN nlIsOne(number a, const coeffs r)
Definition: longrat.cc:2457
poly res
Definition: myNF.cc:322
virtual void Reset()=0
Sets the enumerator to its initial position: -1, which is before the first element in the collection...
single prescision (6,6) real numbers
Definition: coeffs.h:32
#define MP_SMALL
Definition: longrat.cc:154
static number nlLcm(number a, number b, const coeffs r)
Definition: longrat.cc:3300
mpz_t n
Definition: longrat.h:52
const ring r
Definition: syzextra.cc:208
static number nlMapP(number from, const coeffs src, const coeffs dst)
Definition: longrat.cc:188
LINLINE number nlNeg(number za, const coeffs r)
Definition: longrat.cc:2515
number nlXExtGcd(number a, number b, number *s, number *t, number *u, number *v, const coeffs r)
Definition: longrat.cc:2673
float nrFloat(number n)
Converts a n_R number into a float. Needed by Maps.
Definition: shortfl.cc:75
Coefficient rings, fields and other domains suitable for Singular polynomials.
void s_readmpz(s_buff F, mpz_t a)
Definition: s_buff.cc:182
const CanonicalForm CFMap CFMap & N
Definition: cfEzgcd.cc:49
int s_readint(s_buff F)
Definition: s_buff.cc:110
int j
Definition: myNF.cc:70
number nlDiv(number a, number b, const coeffs r)
Definition: longrat.cc:1007
LINLINE number nlMult(number a, number b, const coeffs r)
Definition: longrat.cc:2570
number nlInvers(number a, const coeffs r)
Definition: longrat.cc:653
number _nlCopy_NoImm(number a)
Definition: longrat.cc:1610
#define assume(x)
Definition: mod2.h:394
void _nlInpAdd_aNoImm_OR_bNoImm(number &a, number b)
Definition: longrat.cc:1842
The main handler for Singular numbers which are suitable for Singular polynomials.
Templated enumerator interface for simple iteration over a generic collection of T&#39;s.
Definition: Enumerator.h:124
int nlDivComp(number a, number b, const coeffs r)
Definition: longrat.cc:956
LINLINE void nlInpMult(number &a, number b, const coeffs r)
Definition: longrat.cc:2618
static void nlWriteFd(number n, FILE *f, const coeffs)
Definition: longrat.cc:3180
const ExtensionInfo & info
< [in] sqrfree poly
#define A
Definition: sirandom.c:23
number(* nMapFunc)(number a, const coeffs src, const coeffs dst)
maps "a", which lives in src, into dst
Definition: coeffs.h:73
const ring R
Definition: DebugPrint.cc:36
void _nlDelete_NoImm(number *a)
Definition: longrat.cc:1631
virtual reference Current()=0
Gets the current element in the collection (read and write).
#define LINLINE
Definition: longrat.cc:26
static number nlMapLongR(number from, const coeffs src, const coeffs dst)
Definition: longrat.cc:431
static const int SW_RATIONAL
set to 1 for computations over Q
Definition: cf_defs.h:28
All the auxiliary stuff.
int m
Definition: cfEzgcd.cc:119
#define mpz_isNeg(A)
Definition: longrat.cc:156
const char *const nDivBy0
Definition: numbers.h:83
void On(int sw)
switches
LINLINE BOOLEAN nlEqual(number a, number b, const coeffs r)
Definition: longrat.cc:2430
void nlPower(number x, int exp, number *lu, const coeffs r)
Definition: longrat.cc:1117
#define SSI_BASE
Definition: auxiliary.h:131
FILE * f
Definition: checklibs.c:9
int i
Definition: cfEzgcd.cc:123
void PrintS(const char *s)
Definition: reporter.cc:284
number nlQuotRem(number a, number b, number *r, const coeffs R)
Definition: longrat.cc:2725
static number nlReadFd(s_buff f, const coeffs)
Definition: longrat.cc:3226
void nlInpIntDiv(number &a, number b, const coeffs r)
Definition: longrat.cc:2793
number nlExtGcd(number a, number b, number *s, number *t, const coeffs)
Definition: longrat.cc:2880
LINLINE BOOLEAN nlIsZero(number za, const coeffs r)
Definition: longrat.cc:2466
int IsPrime(int p)
Definition: prime.cc:61
(mpz_ptr), see rmodulon,h
Definition: coeffs.h:115
void nlGMP(number &i, mpz_t n, const coeffs r)
Definition: longrat.cc:1482
static void nlNormalize_Gcd(number &x)
Definition: longrat.cc:1664
BOOLEAN _nlEqual_aNoImm_OR_bNoImm(number a, number b)
Definition: longrat.cc:1563
number nlShort3_noinline(number x)
Definition: longrat.cc:169
static void nlClearContent(ICoeffsEnumerator &numberCollectionEnumerator, number &c, const coeffs cf)
Definition: longrat.cc:2982
static CanonicalForm nlConvSingNFactoryN(number n, const BOOLEAN setChar, const coeffs)
Definition: longrat.cc:336
static FORCE_INLINE n_coeffType getCoeffType(const coeffs r)
Returns the type of coeffs domain.
Definition: coeffs.h:425
int(* siRandProc)()
Definition: sirandom.h:9
int size(const CanonicalForm &f, const Variable &v)
int size ( const CanonicalForm & f, const Variable & v )
Definition: cf_ops.cc:600
number nlBigInt(number &n)
void chineseRemainderCached(CFArray &a, CFArray &n, CanonicalForm &xnew, CanonicalForm &prod, CFArray &inv)
Definition: cf_chinese.cc:264
#define SR_TO_INT(SR)
Definition: longrat.h:70
void gmp_numerator(const CanonicalForm &f, mpz_ptr result)
Definition: singext.cc:20
(number), see longrat.h
Definition: coeffs.h:111
void nlNormalize(number &x, const coeffs r)
Definition: longrat.cc:1349
void chineseRemainder(const CanonicalForm &x1, const CanonicalForm &q1, const CanonicalForm &x2, const CanonicalForm &q2, CanonicalForm &xnew, CanonicalForm &qnew)
void chineseRemainder ( const CanonicalForm & x1, const CanonicalForm & q1, const CanonicalForm & x2...
Definition: cf_chinese.cc:52
number nlChineseRemainderSym(number *x, number *q, int rl, BOOLEAN sym, CFArray &inv_cache, const coeffs CF)
Definition: longrat.cc:2938
const Variable & v
< [in] a sqrfree bivariate poly
Definition: facBivar.h:37
#define mpz_size1(A)
Definition: si_gmp.h:12
n_coeffType
Definition: coeffs.h:27
CanonicalForm cf
Definition: cfModGcd.cc:4024
number _nlNeg_NoImm(number a)
Definition: longrat.cc:1649
#define NULL
Definition: omList.c:10
static number nlShort3(number x)
Definition: longrat.cc:109
static number nlRandom(siRandProc p, number v2, number, const coeffs cf)
Definition: longrat.cc:3310
REvaluation E(1, terms.length(), IntRandom(25))
CanonicalForm den(const CanonicalForm &f)
LINLINE void nlDelete(number *a, const coeffs r)
Definition: longrat.cc:2499
static FORCE_INLINE number n_Div(number a, number b, const coeffs r)
return the quotient of &#39;a&#39; and &#39;b&#39;, i.e., a/b; raises an error if &#39;b&#39; is not invertible in r exceptio...
Definition: coeffs.h:619
BOOLEAN nlDivBy(number a, number b, const coeffs)
Definition: longrat.cc:942
(gmp_float), see
Definition: coeffs.h:117
b *CanonicalForm B
Definition: facBivar.cc:51
#define ABS(x)
Definition: auxiliary.h:111
virtual bool MoveNext()=0
Advances the enumerator to the next element of the collection. returns true if the enumerator was suc...
int gcd(int a, int b)
Definition: walkSupport.cc:839
BOOLEAN nlIsUnit(number a, const coeffs)
Definition: longrat.cc:998
long nlInt(number &n, const coeffs r)
Definition: longrat.cc:603
#define SR_INT
Definition: longrat.h:68
number _nlMult_aImm_bImm_rNoImm(number a, number b)
Definition: longrat.cc:2196
#define ALLOC_RNUMBER()
Definition: coeffs.h:87
nMapFunc nlSetMap(const coeffs src, const coeffs dst)
Definition: longrat.cc:2326
Variable x
Definition: cfModGcd.cc:4023
number _nlAdd_aNoImm_OR_bNoImm(number a, number b)
Definition: longrat.cc:1684
#define GCD_NORM_COND(OLD, NEW)
Definition: longrat.cc:1662
long s_readlong(s_buff F)
Definition: s_buff.cc:138
number nlExactDiv(number a, number b, const coeffs r)
Definition: longrat.cc:733
number _nlSub_aNoImm_OR_bNoImm(number a, number b)
Definition: longrat.cc:1985
number nlMapGMP(number from, const coeffs src, const coeffs dst)
Definition: longrat.cc:205
BOOLEAN nlDBTest(number a, const char *f, const int l)
p exp[i]
Definition: DebugPrint.cc:39
LINLINE number nlInit(long i, const coeffs r)
Definition: longrat.cc:2439
(int), see modulop.h
Definition: coeffs.h:110
#define SR_HDL(A)
Definition: tgb.cc:35
END_NAMESPACE const void * p2
Definition: syzextra.cc:202
static char * nlCoeffString(const coeffs r)
Definition: longrat.cc:3173
static FORCE_INLINE void n_Delete(number *p, const coeffs r)
delete &#39;p&#39;
Definition: coeffs.h:459
number nlMapMachineInt(number from, const coeffs, const coeffs)
Definition: longrat.cc:229
kBucketDestroy & P
Definition: myNF.cc:191
number nlCopyMap(number a, const coeffs, const coeffs)
Definition: longrat.cc:2317
int BOOLEAN
Definition: auxiliary.h:85
static number nlMapR(number from, const coeffs src, const coeffs dst)
Definition: longrat.cc:401
const poly b
Definition: syzextra.cc:213
number nlGetNumerator(number &n, const coeffs r)
Definition: longrat.cc:1532
LINLINE number nlCopy(number a, const coeffs r)
Definition: longrat.cc:2486
void dErrorBreak()
Definition: dError.cc:141
void Werror(const char *fmt,...)
Definition: reporter.cc:189
#define LONG
Definition: longrat.cc:105
return result
Definition: facAbsBiFact.cc:76
int l
Definition: cfEzgcd.cc:94
#define ALLOC0_RNUMBER()
Definition: coeffs.h:88
#define nlTest(a, r)
Definition: longrat.cc:87
const CanonicalForm const CanonicalForm const CanonicalForm const CanonicalForm & cand
Definition: cfModGcd.cc:69
number nlFarey(number nN, number nP, const coeffs CF)
Definition: longrat.cc:2811
void gmp_denominator(const CanonicalForm &f, mpz_ptr result)
Definition: singext.cc:40
coeffs nInitChar(n_coeffType t, void *parameter)
one-time initialisations for new coeffs in case of an error return NULL
Definition: numbers.cc:341
(float), see shortfl.h
Definition: coeffs.h:116
#define omStrDup(s)
Definition: omAllocDecl.h:263