use new ecvt.c from C library
This commit is contained in:
parent
03610bb643
commit
d7d16cbede
1 changed files with 94 additions and 107 deletions
|
@ -1,122 +1,109 @@
|
||||||
/* $Header$ */
|
/* $Header$ */
|
||||||
/*
|
#ifndef NOFLOAT
|
||||||
* (c) copyright 1983 by the Vrije Universiteit, Amsterdam, The Netherlands.
|
|
||||||
*
|
|
||||||
* This product is part of the Amsterdam Compiler Kit.
|
|
||||||
*
|
|
||||||
* Permission to use, sell, duplicate or disclose this software must be
|
|
||||||
* obtained in writing. Requests for such permissions may be sent to
|
|
||||||
*
|
|
||||||
* Dr. Andrew S. Tanenbaum
|
|
||||||
* Wiskundig Seminarium
|
|
||||||
* Vrije Universiteit
|
|
||||||
* Postbox 7161
|
|
||||||
* 1007 MC Amsterdam
|
|
||||||
* The Netherlands
|
|
||||||
*
|
|
||||||
*/
|
|
||||||
|
|
||||||
extern double _fif();
|
static char *cvt();
|
||||||
|
#define NDIGITS 128
|
||||||
|
|
||||||
/*
|
char *
|
||||||
* _ecvt converts to decimal
|
_ecvt(value, ndigit, decpt, sign)
|
||||||
* the number of digits is specified by ndigit
|
double value;
|
||||||
* decpt is set to the position of the decimal point
|
int ndigit, *decpt, *sign;
|
||||||
* sign is set to 0 for positive, 1 for negative
|
|
||||||
*/
|
|
||||||
|
|
||||||
#define NDIG 80
|
|
||||||
|
|
||||||
static char*
|
|
||||||
cvt(arg, ndigits, decpt, sign, eflag)
|
|
||||||
double arg;
|
|
||||||
int ndigits, *decpt, *sign, eflag;
|
|
||||||
{
|
{
|
||||||
register int r2;
|
return cvt(value, ndigit, decpt, sign, 1);
|
||||||
double fi, fj;
|
}
|
||||||
register char *p, *p1;
|
|
||||||
static char buf[NDIG];
|
char *
|
||||||
int i; /*!*/
|
_fcvt(value, ndigit, decpt, sign)
|
||||||
|
double value;
|
||||||
|
int ndigit, *decpt, *sign;
|
||||||
|
{
|
||||||
|
return cvt(value, ndigit, decpt, sign, 0);
|
||||||
|
}
|
||||||
|
|
||||||
|
static struct powers_of_10 {
|
||||||
|
double pval;
|
||||||
|
double rpval;
|
||||||
|
int exp;
|
||||||
|
} p10[] = {
|
||||||
|
1.0e32, 1.0e-32, 32,
|
||||||
|
1.0e16, 1.0e-16, 16,
|
||||||
|
1.0e8, 1.0e-8, 8,
|
||||||
|
1.0e4, 1.0e-4, 4,
|
||||||
|
1.0e2, 1.0e-2, 2,
|
||||||
|
1.0e1, 1.0e-1, 1,
|
||||||
|
1.0e0, 1.0e0, 0
|
||||||
|
};
|
||||||
|
|
||||||
|
static char *
|
||||||
|
cvt(value, ndigit, decpt, sign, ecvtflag)
|
||||||
|
double value;
|
||||||
|
int ndigit, *decpt, *sign;
|
||||||
|
{
|
||||||
|
static char buf[NDIGITS+1];
|
||||||
|
register char *p = buf;
|
||||||
|
register char *pe;
|
||||||
|
|
||||||
|
if (ndigit < 0) ndigit = 0;
|
||||||
|
if (ndigit > NDIGITS) ndigit = NDIGITS;
|
||||||
|
pe = &buf[ndigit];
|
||||||
|
buf[0] = '\0';
|
||||||
|
|
||||||
if (ndigits<0)
|
|
||||||
ndigits = 0;
|
|
||||||
if (ndigits>=NDIG-1)
|
|
||||||
ndigits = NDIG-2;
|
|
||||||
r2 = 0;
|
|
||||||
*sign = 0;
|
*sign = 0;
|
||||||
p = &buf[0];
|
if (value < 0) {
|
||||||
if (arg<0) {
|
|
||||||
*sign = 1;
|
*sign = 1;
|
||||||
arg = -arg;
|
value = -value;
|
||||||
}
|
}
|
||||||
arg = _fif(arg, 1.0, &fi);
|
|
||||||
/*
|
*decpt = 0;
|
||||||
* Do integer part
|
if (value != 0.0) {
|
||||||
*/
|
register struct powers_of_10 *pp = &p10[0];
|
||||||
if (fi != 0) {
|
|
||||||
p1 = &buf[NDIG];
|
if (value >= 10.0) do {
|
||||||
while (fi != 0) {
|
while (value >= pp->pval) {
|
||||||
i = (_fif(fi, 0.1, &fi) + 0.03) * 10;
|
value *= pp->rpval;
|
||||||
*--p1 = i + '0';
|
*decpt += pp->exp;
|
||||||
r2++;
|
}
|
||||||
}
|
} while ((++pp)->exp > 0);
|
||||||
while (p1 < &buf[NDIG])
|
|
||||||
*p++ = *p1++;
|
pp = &p10[0];
|
||||||
} else if (arg > 0) {
|
if (value < 1.0) do {
|
||||||
while ((fj = arg*10) < 1) {
|
while (value * pp->pval < 10.0) {
|
||||||
arg = fj;
|
value *= pp->pval;
|
||||||
r2--;
|
*decpt -= pp->exp;
|
||||||
}
|
}
|
||||||
|
} while ((++pp)->exp > 0);
|
||||||
|
|
||||||
|
(*decpt)++; /* because now value in [1.0, 10.0) */
|
||||||
}
|
}
|
||||||
p1 = &buf[ndigits];
|
if (! ecvtflag) {
|
||||||
if (eflag==0)
|
/* for fcvt() we need ndigit digits behind the dot */
|
||||||
p1 += r2;
|
pe += *decpt;
|
||||||
*decpt = r2;
|
if (pe > &buf[NDIGITS]) pe = &buf[NDIGITS];
|
||||||
if (p1 < &buf[0]) {
|
|
||||||
buf[0] = '\0';
|
|
||||||
return(buf);
|
|
||||||
}
|
}
|
||||||
while (p<=p1 && p<&buf[NDIG]) {
|
while (p <= pe) {
|
||||||
arg = _fif(arg, 10.0, &fj);
|
*p++ = (int)value + '0';
|
||||||
i = fj;
|
value = 10.0 * (value - (int)value);
|
||||||
*p++ = i + '0';
|
|
||||||
}
|
}
|
||||||
if (p1 >= &buf[NDIG]) {
|
if (pe >= buf) {
|
||||||
buf[NDIG-1] = '\0';
|
p = pe;
|
||||||
return(buf);
|
*p += 5; /* round of at the end */
|
||||||
}
|
while (*p > '9') {
|
||||||
p = p1;
|
*p = '0';
|
||||||
*p1 += 5;
|
if (p > buf) ++*--p;
|
||||||
while (*p1 > '9') {
|
else {
|
||||||
*p1 = '0';
|
*p = '1';
|
||||||
if (p1>buf) {
|
++*decpt;
|
||||||
p1--; *p1 += 1;
|
if (! ecvtflag) {
|
||||||
} else {
|
/* maybe add another digit at the end,
|
||||||
*p1 = '1';
|
because the point was shifted right
|
||||||
(*decpt)++;
|
*/
|
||||||
if (eflag==0) {
|
if (pe > buf) *pe = '0';
|
||||||
if (p>buf)
|
pe++;
|
||||||
*p = '0';
|
}
|
||||||
p++;
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
*pe = '\0';
|
||||||
}
|
}
|
||||||
*p = '\0';
|
return buf;
|
||||||
return(buf);
|
|
||||||
}
|
|
||||||
|
|
||||||
char*
|
|
||||||
_ecvt(arg, ndigits, decpt, sign)
|
|
||||||
double arg;
|
|
||||||
int ndigits, *decpt, *sign;
|
|
||||||
{
|
|
||||||
return(cvt(arg, ndigits, decpt, sign, 1));
|
|
||||||
}
|
|
||||||
|
|
||||||
char*
|
|
||||||
_fcvt(arg, ndigits, decpt, sign)
|
|
||||||
double arg;
|
|
||||||
int ndigits, *decpt, *sign;
|
|
||||||
{
|
|
||||||
return(cvt(arg, ndigits, decpt, sign, 0));
|
|
||||||
}
|
}
|
||||||
|
#endif
|
||||||
|
|
Loading…
Add table
Reference in a new issue