Hi,

I'm not quite sure what you're looking for.

I was just curious if there's any way to do large numbers of + - operations with the knowingness that they're not information-destructive whatsoever. Possibly * and / too. And I see that's doable - neat!

2012/2/4 Bradley Lucier <lucier@math.purdue.edu>

On Feb 4, 2012, at 4:45 AM, Mikael wrote:

> Dear Marc or Brad, I'd be curious to know if there is any way to ensure that calculations in Gambit become completely exact?
>
> What I'm looking for is that as flonum operations by nature are inexact (+ 0.1 0.2 would be a good example), would there be a way to use bignum-only operations, or have some kind of configuration that uses fixnum when applicable and otherwise bignum only.

Do you mean floating-point numbers with parametrized precision?  Or do you mean something like this:

[Bradley-Luciers-MacBook-Pro:~] lucier% gsi
Gambit v4.6.3

> (+ #e1.2 #e3.77)
497/100

When I wrote my homework-on-the web system, there was code like

(define (exact-string->number s)
 (string->number (string-append "#e" s)))

to make sure that some of the conversions were exact.

Wow that's neat!

(exact->inexact (+ #e0.2 #e0.1)) indeed produces 0.3 . Same with multiplication:

> (* 0.2 0.1)
.020000000000000004
> (exact->inexact (* #e0.2 #e0.1))
.02

> (/ 0.3 0.2)
1.4999999999999998
> (exact->inexact (/ #e0.3 #e0.2))
1.5

And it certainly works in a wider scope too. :)
> (* 12938209384.11111111111111111111113 984537862.222222222222229999933333330000000011111111119999999999922222222222222224)
1.2738157008016247e19
> (* #e12938209384.11111111111111111111113 #e984537862.222222222222229999933333330000000011111111119999999999922222222222222224)
79613481300101548404321616589664132883905299223332442517547118401117606549391743970919425255555546373456790123457/6250000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000

I suppose to get all/a fixed number of decimals, one needs to make a custom variant of exact->inexact? (I suppose what this one does is to fill up a flonum)
> (exact->inexact #)
1.2738157008016247e19

Apparently you must use #e rather than inexact->exact to get exact numbers, the latter does something else
> (exact->inexact (+ (inexact->exact 0.1) (inexact->exact 0.2)))
.30000000000000004

Based on inspiration from Gambits sources one could make a (make-number-exact n) routine faster than one defined as (exact-string->number (number->string n)).


I suppose for any number of the form [-]digits dot digits, converting numbers to bignum (as you mention below) and then doing bignum+ on them is faster than the #e route.

> Is there anything like this - I know fixnum and flonum ops can be accessed under fixnum+ etc., but what about the bignums, (bignum+ 99999999999999999999 2)?

Well, simple + will do this,

calling ##+ to convert the 2 to a (non-normalized) bignum,

Can you give a code example on this one?

Also a modified string->number should be able to produce bignums straight.
 
and then calling ##bignum.+ on the pair.

There are ways to compute with the so-called "constructive reals" or "computable reals" (I have the beginnings of such a package, and several packages using different underlying representations exist for Common Lisp), but is that what you want?

What's this about?

> Afaik the bignum library is completely exact for + and -, and has a precision of at least 10^-17 for the rest of the operations (* / modulo sqrt expt etc), is this the way?

*, modulo and expt are exact (if the first argument to expt is exact and the second is an integer), there is integer-sqrt, which gives you a square root and a remainder.

/ gives you an exact rational when handed two exact integers.

Cool!

Is there any way to perform fixed-point arithmetics on selected operations (to 3, 6, 9 etc decimals) (I think you call this floating-point with parameterized precision), maybe using a bignum-truncate-to-decimals?

Brad

Kind regards, Mikael