简体   繁体   中英

Implementing cos(x) by its Taylor series in python

I have to implement the cosine function in python by using its Taylor series. I have to print its values and the absolute and relative errors for all the values in listt from below. Here is what I tried:

import math

def expression(x, k):
   return (-1)**k/(math.factorial(2*k))*(x**(2*k))
pi=math.pi
listt=[0, pi/6, pi/4, pi/3, pi/2, (2*pi)/3, (3*pi)/4, (5*pi)/6, pi]
sum=0
for x in listt:
   k=0
   relative_error=1
   while relative_error>10**(-15):
       sum+=expression(x, k)
       absolute_error=abs(math.cos(x)-sum)
       relative_error=absolute_error/abs(math.cos(x))
       k+=1
    print("%.20f"%x, '\t', "%.20f"%sum, '\t', "%.20f"%math.cos(x), '\t', "%.20f"%absolute_error, '\t', "%.20f"%relative_error )

This, however, produces a huge error. The cause is probably that I perform all those subtractions. However, I don't know how to avoid them. I ran into the same problem when computing e^x for negative x, but there I just computed e^(-x) if x was negative and I could then just write that e^x=1/e^(-x). Is there some similar trick here?
Also, note that my while is infinite, because the relative error is always huge.

Fatal error: You set sum=0 outside the loop over the test points. You need to reset it for every test point. This error could be easily avoided if you made the approximate cosine computation a separate function.


It is always a better idea to compute the terms of the series by multiplying with the quotient to the previous term. This avoids the computation of the factorial and all the difficulties that its growth may produce.

That said, the growth of terms is the same as those for the exponential series, so the largest term is where 2*k is about |x| . For the given points that should not be prohibitively large.

To be a little more precise, the error of a cosine partial sum is smaller than the next term, as the series is alternating. The term of degree 2*k for |x|<=4 has the approximate bound, using Stirling's formula for the factorial,

4^(4*k)/(4*k/e)^(4*k) = (e/k)^(4*k) < (3/k)^(4*k)

which for k=6 gives an upper bound of 2^(-24) ~ 10^(-7) . Thus there should be no catastrophic errors for the test values.

See also Calculate maclaurin series for sin using C , Issue with program to approximate sin and cosine values , Sine calculation with Taylor series not working

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM