Re: Inaccurate results from numeric ln(), log(), exp() and pow() - Mailing list pgsql-hackers

From Dean Rasheed
Subject Re: Inaccurate results from numeric ln(), log(), exp() and pow()
Date
Msg-id CAEZATCVvKt=JCP43JhoB26MBZCy53w3Pa5Wwuv73GdpyN6_Bkg@mail.gmail.com
Whole thread Raw
In response to Re: Inaccurate results from numeric ln(), log(), exp() and pow()  (Tom Lane <tgl@sss.pgh.pa.us>)
Responses Re: Inaccurate results from numeric ln(), log(), exp() and pow()  (Tom Lane <tgl@sss.pgh.pa.us>)
Re: Inaccurate results from numeric ln(), log(), exp() and pow()  (Dean Rasheed <dean.a.rasheed@gmail.com>)
List pgsql-hackers
On 13 November 2015 at 18:36, Tom Lane <tgl@sss.pgh.pa.us> wrote:
> Next question: in the additional range-reduction step you added to ln_var,
> why stop there, ie, what's the rationale for this magic number:
>
>         if (Abs((x.weight + 1) * DEC_DIGITS) > 10)
>
> Seems like we arguably should do this whenever the weight isn't zero,
> so as to minimize the number of sqrt() steps.  (Yes, I see the point
> about not getting into infinite recursion, but that only says that
> the threshold needs to be more than 10, not that it needs to be 10^10.)
>

It's a bit arbitrary. There is a tradeoff here -- computing ln(10) is
more expensive than doing a sqrt() since the Babylonian algorithm used
for sqrt() is quadratically convergent, whereas the Taylor series for
ln() converges more slowly. At the default precision, ln(10) is around
7 times slower than sqrt() on my machine, although that will vary with
precision, and the sqrt()s increase the local rscale and so they will
get slower. Anyway, it seemed reasonable to not do the extra ln()
unless it was going to save at least a couple of sqrt()s.


> Also, it seems a little odd to put the recursive calculation of ln(10)
> where you did, rather than down where it's used, ie why not
>
>                 mul_var(result, &fact, result, local_rscale);
>
>                 ln_var(&const_ten, &ln_10, local_rscale);
>                 int64_to_numericvar((int64) pow_10, &ni);
>                 mul_var(&ln_10, &ni, &xx, local_rscale);
>                 add_var(result, &xx, result);
>
>                 round_var(result, rscale);
>
> As you have it, ln_10 will be calculated with possibly a smaller rscale
> than is used in this stanza.  That might be all right but it seems dubious
> --- couldn't the lower-precision result leak into digits we care about?
>

Well it still has 8 digits more than the final rscale, so it's
unlikely to cause any loss of precision when added to the result and
then rounded to rscale. But on the other hand it does look neater to
compute it there, right where it's needed.

Regards,
Dean



pgsql-hackers by date:

Previous
From: "David G. Johnston"
Date:
Subject: Re: proposal: multiple psql option -c
Next
From: Dean Rasheed
Date:
Subject: Re: Inaccurate results from numeric ln(), log(), exp() and pow()