-2

I've been trying to create a program that can calculate the cos of a radiant using Taylor series. I contemplate the error, for example:

cos(45)=1.4 must be this : s=(((-1.)**n/(fact*2.*n))*x**(2.*n))*sign.

The code:

program project2_ex6
implicit none
!Reference to variables
!-------------------------------------------------------
integer(kind=3)::degrees,i,sign !sign=a random name in order to use it to change the 's' sign consecutively
integer::n
double precision::x,err_limit,s_old,s,fact !x=angle in radiants,err_limit=the absolute error between two results,fact=factorial
real,parameter::pi=3.14159265359
!------------------------------------------------------
print*,'This program calculates the cos(x)'
print*,"Enter the angle's degrees"
read*,degrees
!Checking validity of degrees
!----------------------------------------------------
do
if(degrees<0.or.degrees>360) then
  print*,'Degrees must be between 0-360'
  else
   x=pi*degrees/180
    exit
    end if
    end do
    sign=1
    sign=sign*(-1)
    err_limit=1e-5
 n=0
    s=0
    s_old=0
    fact=1
!Commencing do loop
!-----------------------------------------------------------
do
  do i=1,n
    fact=fact*i
    end do
    if(n==0) then
      s=1
      else
  s=(((-1.)**n/(fact*2.*n))*x**(2.*n))*sign
 s=s+s_old
end if
n=n+1
if(abs(s-s_old)<err_limit) then
  exit
  else
    s_old=s
    cycle
    end if
  end do
  !Printing results
!-----------------------------------------------------------------
  print*,s,i,n
  end program
  • 3
    You should reference your older question http://stackoverflow.com/questions/33671576/fortran-error-when-calculating-cosx and state what is different. What do you get as a result? Why do you believe there is an error in your code? I really recommend you to NOT use `integer(kind=3)`, you are just asking for trouble in the future. Read http://stackoverflow.com/questions/3170239/fortran-integer4-vs-integer4-vs-integerkind-4 – Vladimir F Героям слава Nov 21 '15 at 19:58
  • 4
    Also, to ease reading of your code by us, by your teacher and by you, align vertically the corresponding `if` and `end if` and the corresponding `do` and `end do`. Do not just jump from one column to another. This is called indentation and it is really important (http://www.fortran90.org/src/best-practices.html). – Vladimir F Героям слава Nov 21 '15 at 20:01

1 Answers1

1

I found four mistakes:-

(1) fact should be set to 1 inside the main DO loop

(2) fact should be multiplied by itself 2n times in the inner DO loop

(3) In the main calculation of s, the denominator should be fact, not fact*2*n

(4) In the main calculation of s, don't need to multiply by sign (or if you do, it should be +1)

This now gives 0.7071... for 45 degrees.

program project2_ex6
implicit none
!Reference to variables
!-------------------------------------------------------
integer::degrees,i,sign !sign=a random name in order to use it to change the 's' sign consecutively
integer::n
double precision::x,err_limit,s_old,s,fact !x=angle in         radiants,err_limit=the absolute error between two results,fact=factorial
real,parameter::pi=3.14159265359
!------------------------------------------------------
print*,'This program calculates the cos(x)'
print*,"Enter the angle's degrees"
read*,degrees
!Checking validity of degrees
!----------------------------------------------------
do
 if(degrees<0.or.degrees>360) then
  print*,'Degrees must be between 0-360'
 else
   x=pi*degrees/180
    exit
  end if
end do
    sign=1
!
! Sign should be +1 or omitted
!
!-   sign=sign*(-1)
 err_limit=1e-5
 n=0
 s=0
 s_old=0

!Commencing do loop
!-----------------------------------------------------------
do
!
! Initialise fact inside do loop
!
  fact=1
!
! Change n to 2n
!
  do i=1,2*n
    fact=fact*i
   end do
  if(n==0) then
     s=1
  else
!
!Change fact*2*n to fact
!
    s=(((-1.)**n/(fact))*x**(2.*n))*sign
    s=s+s_old
  end if
 n=n+1
 if(abs(s-s_old)<err_limit) then
  exit
 else
    s_old=s
    cycle
    end if
end do
  !Printing results
!-----------------------------------------------------------------
 print*,s,i,n
 end program
Tom Sharpe
  • 30,727
  • 5
  • 24
  • 37
  • Although for many degrees now I get 'floating point arithmetic overflow'(I don't know why),it seems that now a small angle's degrees can be calculated correctly.Thank you a lot for your time,I really appreciate it! – Nikos Ellinakis Nov 22 '15 at 12:10
  • 1
    No problem. I don't know why you get the overflow, but there is an alternative way of doing it where you calculate each term t in the expansion from the previous term tprev using t=tprev*(-1)*x**2/(2*n-1)/(2*n) which might avoid overflows. – Tom Sharpe Nov 23 '15 at 09:20