Velocity Reviews > Precision upto n decimal points

# Precision upto n decimal points

Pp
Guest
Posts: n/a

 12-04-2011
I am writing power series expansion programs.

For eg.
e^x = 1 + x + x^2/2! + x^3/3! + .....

Depending on how much precision I need, how do I stop the expansion.

For eg. if I need up to precision 5 then my loop will run in the form

double ex;
double newterm;
// new term is 1 in first iteration
// is x in 2nd iteration
// is x^2/2! in 3rd iteration & so on.

do
{

calculate newterm;

ex = ex + newterm;

} while (newterm > 1.0e-5);

Is the right way to do it or is there a better way do this?

What about for expansions for stuff like cos(x), sin(x) where negative
terms are involved?

Nick Keighley
Guest
Posts: n/a

 12-04-2011
On Dec 4, 10:57*am, Pp <(E-Mail Removed)> wrote:

> I am writing power series expansion programs.
>
> For eg.
> e^x = 1 + x + x^2/2! + x^3/3! + .....
>
> Depending on how much precision I need, how do I stop the expansion.

when you've reached the required precision

> For eg. if I need up to precision 5 then my loop will run in the form
>
> double ex;
> double newterm;
> // new term is 1 in first iteration
> // is x in 2nd iteration
> // is x^2/2! in 3rd iteration & so on.
>
> do
> {
> * * * * calculate newterm;
> * * * * ex = ex + newterm;
> } while (newterm > 1.0e-5);
>
> Is the right way to do it or is there a better way do this?

given that IANA Numerical Analalyst, yes looks fine to me

> What about for expansions for stuff like cos(x), sin(x) where negative
> terms are involved?

> } while (fabs(newterm) > 1.0e-5);

perhaps?

Tim Prince
Guest
Posts: n/a

 12-04-2011
On 12/4/2011 5:57 AM, Pp wrote:
> I am writing power series expansion programs.
>
> For eg.
> e^x = 1 + x + x^2/2! + x^3/3! + .....
>
> Depending on how much precision I need, how do I stop the expansion.
>
> For eg. if I need up to precision 5 then my loop will run in the form
>
>
> double ex;
> double newterm;
> // new term is 1 in first iteration
> // is x in 2nd iteration
> // is x^2/2! in 3rd iteration & so on.
>
> do
> {
>
> calculate newterm;
>
> ex = ex + newterm;
>
> } while (newterm > 1.0e-5);
>
> Is the right way to do it or is there a better way do this?
>
> What about for expansions for stuff like cos(x), sin(x) where negative
> terms are involved?
>

When you have performed range reduction (taking advantage of the
periodicity), so that your series covers at most 2 quadrants, you can
figure out ahead of time the number of terms you require, and apply
Horner evaluation. Methods such as Chebyshev economization will improve
the convergence rate of the series on the fixed interval.

--
Tim Prince

Barry Schwarz
Guest
Posts: n/a

 12-04-2011
On Sun, 04 Dec 2011 16:27:37 +0530, Pp <(E-Mail Removed)> wrote:

>I am writing power series expansion programs.
>
>For eg.
>e^x = 1 + x + x^2/2! + x^3/3! + .....
>
>Depending on how much precision I need, how do I stop the expansion.
>
>For eg. if I need up to precision 5 then my loop will run in the form
>
>
>double ex;
>double newterm;
>// new term is 1 in first iteration
>// is x in 2nd iteration
>// is x^2/2! in 3rd iteration & so on.
>
>do
>{
>
> calculate newterm;
>
> ex = ex + newterm;
>
>} while (newterm > 1.0e-5);

This only works if the fabs(final value) < 10.

If x is 15, then the answer to five significant digits is 3.2690e+6
and, using your philosophy, you should stop when newterm < 1e+5.

Basically, the limit you test against needs to be scaled by both the
number of significant digits and the base 10 log of the final value.

>
>Is the right way to do it or is there a better way do this?

In your example, let us assume that newterm falls below the test limit
in iteration N. You now have a five digit value ABCDE and some
indication of where to insert the decimal point. It is still possible
that executing the loop another dozen (or hundred) times will update
the value to ABCDF. You need to understand how Numerical Analysis is
capable of determining the maximum error after a particular iteration.

>What about for expansions for stuff like cos(x), sin(x) where negative
>terms are involved?

Still part of Numerical Analysis.

--
Remove del for email

Eric Sosman
Guest
Posts: n/a

 12-04-2011
On 12/4/2011 5:57 AM, Pp wrote:
> I am writing power series expansion programs.
>
> For eg.
> e^x = 1 + x + x^2/2! + x^3/3! + .....
>
> Depending on how much precision I need, how do I stop the expansion.
>
> For eg. if I need up to precision 5 then my loop will run in the form
>
>
> double ex;
> double newterm;
> // new term is 1 in first iteration
> // is x in 2nd iteration
> // is x^2/2! in 3rd iteration & so on.
>
> do
> {
>
> calculate newterm;
>
> ex = ex + newterm;
>
> } while (newterm > 1.0e-5);
>
> Is the right way to do it or is there a better way do this?

This will work for the series you mention, and for many others.
It might fail for some peculiar kinds of series, like x^3*e^x (the
expansion consists of the series you show, but with three zeroes
tacked on at the start; your criterion would stop at the first zero
and never evaluate the remaining terms).

Also, note that "newterm is small" does not necessarily imply
that the sum is accurate. For example, consider the harmonic series
1, 1/2, 1/3, ... Your loop would stop after around ten thousand terms
and would announce that the series adds to about 9.79. Alas, the
harmonic series does not converge at all! The terms get smaller, yes,
but they do not get small "fast enough" for convergence. So, beware!

> What about for expansions for stuff like cos(x), sin(x) where negative
> terms are involved?

The fabs() function is your friend ...

Many iterative numerical calculations use two (or even more)
stopping criteria: They'll stop after the calculation converges to
a suitable accuracy, or they'll stop and announce failure if the
calculation just buzzes around and around and doesn't converge.

--
Eric Sosman
http://www.velocityreviews.com/forums/(E-Mail Removed)d

James Kuyper
Guest
Posts: n/a

 12-04-2011
On 12/04/2011 05:57 AM, Pp wrote:
> I am writing power series expansion programs.
>
> For eg.
> e^x = 1 + x + x^2/2! + x^3/3! + .....
>
> Depending on how much precision I need, how do I stop the expansion.
>
> For eg. if I need up to precision 5 then my loop will run in the form
>
>
> double ex;
> double newterm;
> // new term is 1 in first iteration
> // is x in 2nd iteration
> // is x^2/2! in 3rd iteration & so on.
>
> do
> {
>
> calculate newterm;
>
> ex = ex + newterm;
>
> } while (newterm > 1.0e-5);
>
> Is the right way to do it or is there a better way do this?

Other people have answered your direct question; I'll deal with a slight
different issue. You're targeting a fixed precision of 1e-5, which may
be entirely appropriate approach for a particular problem. However, it's
not uncommon, for a general purpose function, to want to achieve the
maximum precision that's possible. There's a very simple way to impose
that requirement:

double ex, newterm, last;

ex = initial_estimate;

do
{
last = ex;
// calculate newterm
ex = ex + newterm;
} while (ex != last);

> What about for expansions for stuff like cos(x), sin(x) where negative
> terms are involved?

With the approach I just outlined, it doesn't matter whether newterm is
positive or negative.
--
James Kuyper

Weland
Guest
Posts: n/a

 12-04-2011
On 2011-12-04, Pp <(E-Mail Removed)> wrote:
> I am writing power series expansion programs.
>
> For eg.
> e^x = 1 + x + x^2/2! + x^3/3! + .....
>
> Depending on how much precision I need, how do I stop the expansion.
> [...]
> What about for expansions for stuff like cos(x), sin(x) where negative
> terms are involved?
>

Store two consecutive approximations and compute their difference? At least
that's how I saw it done most of the time.

So if e^x = s(1) + s(2) + ... + s(n) + ...

then two consecutive approximations would be

e^x_(k) = s(1) + s(2) + ... + s(k)
e^x_(k+1) = s(1) + s(2) + ... + s(k) + s(k+1)

and the stopping criteria would be

abs(e^x_(k)) - abs(e^x(k+1)) < some threshold

Feel free to jug the abs()s around depending on how you expect the series
expansion to go (e.g. depending on it being monotonically increasing or not,
or if you're expanding around a function's 0 point and you're concerned
about it swinging above and below 0).

Depending on what you're trying to achieve you might also be better
off checking against a relative error, not an absolute one.

--
(E-Mail Removed)
SDF Public Access UNIX System - http://sdf.org
% grep me no patterns and I'll tell you no lines

Lauri Alanko
Guest
Posts: n/a

 12-04-2011
In article <jbg2on\$b8b\$(E-Mail Removed)>,
James Kuyper <(E-Mail Removed)> wrote:
> do
> {
> last = ex;
> // calculate newterm
> ex = ex + newterm;
> } while (ex != last);

That seems dangerous. Depending on the calculation, ex might
eventually oscillate between two numbers. Comparing floats for
equality is in general a bad idea, unless you know really well what
you are doing.

Lauri

James Kuyper
Guest
Posts: n/a

 12-04-2011
On 12/04/2011 10:29 AM, Lauri Alanko wrote:
> In article <jbg2on\$b8b\$(E-Mail Removed)>,
> James Kuyper <(E-Mail Removed)> wrote:
>> do
>> {
>> last = ex;
>> // calculate newterm
>> ex = ex + newterm;
>> } while (ex != last);

>
> That seems dangerous. Depending on the calculation, ex might
> eventually oscillate between two numbers. Comparing floats for
> equality is in general a bad idea, unless you know really well what
> you are doing.

Yes, that approach requires that the sum of the series converges; a
novice shouldn't even attempt doing a partial sum of a non-convergent
series, and an expert needs to be very careful about determining the
best number of terms to use.
Also, a series that converges mathematically might not do so when using
floating point math on a computer - again, that's an issue for experts
to deal with, there's no easy solution for the novice to learn.
--
James Kuyper

gwowen
Guest
Posts: n/a

 12-05-2011
On Dec 4, 10:57*am, Pp <(E-Mail Removed)> wrote:

> do
> {
> * * * * calculate newterm;
> * * * * ex = ex + newterm;
> } while (newterm > 1.0e-5);

what if the nth term is 1.0e-6 for all n?

> Is the right way to do it

No. The nth term being small does not guarantee that the sum of the
nth->infinity will be similarly small.

> or is there a better way do this?

No. There is no general way to determine if a given series will
converge, let alone whether it *has* converged. For specific examples,
you may be able to bound the sum of the tail of the series and use
that bound.