source: git/Singular/longrat0.cc @ 0e1846

fieker-DuValspielwiese
Last change on this file since 0e1846 was 0e1846, checked in by Olaf Bachmann <obachman@…>, 27 years ago
This commit was generated by cvs2svn to compensate for changes in r59, which included commits to RCS files with non-trunk default branches. git-svn-id: file:///usr/local/Singular/svn/trunk@60 2c84dea3-7e68-4137-9b89-c4e89433aadc
  • Property mode set to 100644
File size: 4.7 KB
Line 
1/****************************************
2*  Computer Algebra System SINGULAR     *
3****************************************/
4static char rcsid[] = "$Header: /exports/cvsroot-2/cvsroot/Singular/longrat0.cc,v 1.1.1.1 1997-03-19 13:18:49 obachman Exp $";
5/* $Log: not supported by cvs2svn $
6*/
7/*1
8* ABSTRACT -
9* IO for long rational numbers (Hubert Grassmann)
10*/
11
12#include <stdio.h>
13#include <string.h>
14#include "mod2.h"
15#include "tok.h"
16#include "mmemory.h"
17#include "febase.h"
18#include "longrat.h"
19
20#ifdef HAVE_GMP
21
22#define SR_HDL(A) ((long)(A))
23#define SR_INT    1
24#define INT_TO_SR(INT)  ((number) (((long)INT << 2) + SR_INT))
25#define SR_TO_INT(SR)   (((long)SR) >> 2)
26
27
28/*2
29* extracts a long integer from s, returns the rest
30*/
31char * nlEatLong(char *s, MP_INT *i)
32{
33  char * start=s;
34
35  while (*s >= '0' && *s <= '9') s++;
36  if (*s=='\0')
37  {
38    mpz_set_str(i,start,10);
39  }
40  else
41  {
42    char c=*s;
43    *s='\0';
44    mpz_set_str(i,start,10);
45    *s=c;
46  }
47  return s;
48}
49
50/*2
51* extracts the number a from s, returns the rest
52*/
53char * nlRead (char *s, number *a)
54{
55  if (*s<'0' || *s>'9')
56  {
57    *a = nlInit(1);
58    return s;
59  }
60  *a=(number)Alloc(sizeof(rnumber));
61  {
62    (*a)->s = 3;
63#ifdef LDEBUG
64    (*a)->debug=123456;
65#endif
66    MP_INT *z=&((*a)->z);
67    MP_INT *n=&((*a)->n);
68    mpz_init(z);
69    s = nlEatLong(s, z);
70    if (*s == '/')
71    {
72      mpz_init(n);
73      (*a)->s = 0;
74      s++;
75      s = nlEatLong(s, n);
76      if (mpz_cmp_si(n,(long)0)==0)
77      {
78        PrintS("\nZero Denominator\n");
79        mpz_clear(n);
80        (*a)->s = 3;
81      }
82      else if (mpz_cmp_si(n,(long)1)==0)
83      {
84        mpz_clear(n);
85        (*a)->s=3;
86      }
87    }
88    if (mpz_cmp_si(z,(long)0)==0)
89    {
90      *a=INT_TO_SR(0);
91    }
92    else
93    if ((*a)->s==3)
94    {
95      int ui=(int)mpz_get_si(&(*a)->z);
96      if ((((ui<<3)>>3)==ui)
97      && (mpz_cmp_si(&(*a)->z,(long)ui)==0))
98      {
99        mpz_clear(&(*a)->z);
100        Free((ADDRESS)(*a),sizeof(rnumber));
101        (*a)=INT_TO_SR(ui);
102      }
103    }
104    else
105      nlNormalize(*a);
106  }
107  return s;
108}
109
110/*2
111* write a rational number
112*/
113void nlWrite (number &a)
114{
115  char *s,*z;
116  if (SR_HDL(a) & SR_INT)
117  {
118    StringAppend("%d",SR_TO_INT(a));
119  }
120#ifdef TEST
121  else if (a==NULL)
122  {
123    StringAppend("o");
124  }
125#endif
126  else
127  {
128    if (a->s==0)
129    {
130      nlNormalize(a);
131      nlWrite(a);
132      return;
133    }
134    int l=mpz_sizeinbase(&a->z,10);
135    if (a->s<2) l=max(l,mpz_sizeinbase(&a->n,10));
136    l+=2;
137    s=(char*)Alloc(l);
138    z=mpz_get_str(s,10,&a->z);
139    StringAppend(z);
140    if (a->s!=3)
141    {
142      StringAppend("/");
143      z=mpz_get_str(s,10,&a->n);
144      StringAppend(z);
145    }
146    Free((ADDRESS)s,l);
147  }
148}
149
150#else
151#define NLLENGTH(a) ((int)(*(a)&0X7FFF))
152#define NUM_BASIS 10000
153#define NLISRAT(a)   ((a)->s)
154
155/*3
156* extracts a long integer from s, returns the rest
157*/
158static char * nlEatLong(char *s, number *i)
159{
160  number j, k, ten, n;
161  j = nlInit(0);
162  ten = nlInit(10);
163  while (*s >= '0' && *s <= '9')
164  {
165    k = nlMult(j, ten);
166    nlDelete(&j);
167    j = nlInit((int)*s-(int)'0');
168    s++;
169    n = nlAdd(j, k);
170    nlDelete(&j);
171    nlDelete(&k);
172    j = n;
173  }
174  nlDelete(&ten);
175  *i = j;
176  return s;
177}
178
179/*2
180* extracts the numberio a from s, returns the rest
181*/
182char * nlRead (char *s, number *a)
183{
184  number z, n;
185  BOOLEAN neg = (*s == '-');
186
187  if (*s == '+' || *s == '-')
188    s++;
189  if (*s<'0' || *s>'9')
190  {
191    if (neg)
192      *a = nlInit(-1);
193    else
194      *a = nlInit(1);
195    return s;
196  }
197  s = nlEatLong(s, &z);
198  if (neg)
199    nlNeg(z);
200  *a = z;
201  if (*s == '/')
202  {
203    s++;
204    s = nlEatLong(s, &n);
205    if (nlIsZero(n))
206    {
207      Werror("Zero Denominator");
208      nlDelete(&n);
209      nlDelete(a);
210      return s;
211    }
212    if (nlIsOne(n))
213      nlDelete(&n);
214    else
215    {
216      *a = nlDiv(z, n);
217      nlNormalize(*a);
218    }
219  }
220  return s;
221}
222
223/*3
224* write long integer, assume n!=NULL
225*/
226static void nlWriteLong(lint n)
227{
228  char save;
229  char *lonstr, *str1;
230  int i, k, j;
231  lint a;
232  int16 al, w;
233  al = NLLENGTH(n);
234  k = al+1;
235  i = k*sizeof(int16);
236  a = (lint)Alloc(i);
237  memcpy(a, n, i);
238  j = k*5*sizeof(char);
239  lonstr = (char *)Alloc(j);
240  str1 = lonstr+(k*5-1);
241  *str1 = '\0';
242  do
243  {
244    nlDivMod(a, al, NUM_BASIS, &w);
245    save = *str1;
246    str1 -= 4;
247    sprintf(str1, "%04u", w);
248    str1[4] = save;
249    if (a[al]==0)
250      al--;
251  } while (al!=0);
252  Free((ADDRESS)a,i);
253  while (*str1 == '0') str1++;
254  StringAppend(str1);
255  Free((ADDRESS)lonstr, j);
256}
257
258/*2
259* write a number
260*/
261void nlWrite (number &a)
262{
263  if (nlIsZero(a))
264  {
265    StringAppend("0");
266    return;
267  }
268  if (!nlGreaterZero(a))
269  {
270    StringAppend("-");
271  }
272  if (a->s<0)
273    nlNormalize(a);
274  nlWriteLong(a->z);
275  if (NLISRAT(a))
276  {
277    StringAppend("/");
278    nlWriteLong(a->n);
279  }
280}
281#endif
282
Note: See TracBrowser for help on using the repository browser.