Thread: Segmentation fault (core dumped), e^x taylor expansion question

  1. #1
    Registered User
    Join Date
    Feb 2013
    Posts
    5

    Segmentation fault (core dumped), e^x taylor expansion question

    I am trying to write a program which should calculate, e^x with taylor series expansion, but when i tried big numbers like e^70, i got segmentation fault error, Can you please help me. Code is like that;

    Code:
    #include<stdio.h>
    #include<math.h>
    double factoriel(int n)
    {
      if(n==0 || n==1)
        return 1;
      else 
        return (n*factoriel(n-1));
    }
    double taylor(int n)
    {
      int k=0;
      double sum=0;
      double term;
      while(1)
        {
          term= (double)pow(n,k)/factoriel(k) ;
          sum +=term;
          if(fabs(term)<0.00001)
          break;
          k++;
        }
      return sum;
    }
    
    int main()
    {
      int num;
      printf("Enter a number: ");
      scanf("%d",&num);
        if (num<0)
        printf("e^%d = %4e\n",num,1/taylor( fabs(num) ));
        else
        printf("e^%d = %4e\n",num,taylor(num)); 
    }

  2. #2
    TEIAM - problem solved
    Join Date
    Apr 2012
    Location
    Melbourne Australia
    Posts
    1,907
    You shouldn't use recursion for finding the factorial of a large number -> Using a for loop is faster and there is no risk of stack overflow.
    Fact - Beethoven wrote his first symphony in C

  3. #3
    SAMARAS std10093's Avatar
    Join Date
    Jan 2011
    Location
    Nice, France
    Posts
    2,694
    While Click_here is right, I would like to say that line 19 has the problem. It won't enter the if statement, thus you have a never-ending loop...
    Code - functions and small libraries I use


    It’s 2014 and I still use printf() for debugging.


    "Programs must be written for people to read, and only incidentally for machines to execute. " —Harold Abelson

  4. #4
    Registered User
    Join Date
    Feb 2013
    Posts
    5
    Quote Originally Posted by std10093 View Post
    While Click_here is right, I would like to say that line 19 has the problem. It won't enter the if statement, thus you have a never-ending loop...
    indeed, it is entering the if statement, as the term increase, it is decreasing alot, that's why we are ignoring high terms while using approximations, and the code find quite good results until e^63, but after that, i am getting segmentation error.

  5. #5
    Registered User
    Join Date
    Feb 2013
    Posts
    5
    Quote Originally Posted by Click_here View Post
    You shouldn't use recursion for finding the factorial of a large number -> Using a for loop is faster and there is no risk of stack overflow.
    i tried but same problem arising again,
    thank you anyway.

  6. #6
    TEIAM - problem solved
    Join Date
    Apr 2012
    Location
    Melbourne Australia
    Posts
    1,907
    What happens when int k overflows?
    Fact - Beethoven wrote his first symphony in C

  7. #7
    Registered User
    Join Date
    Feb 2013
    Posts
    5
    cursor continues blinking, and it keeps going, nothing happening, after waiting alot, i am getting segmentation error.

  8. #8
    TEIAM - problem solved
    Join Date
    Apr 2012
    Location
    Melbourne Australia
    Posts
    1,907
    First of all, you do NOT want to try and find the factorial of a negative number

    Put this into your code:
    Code:
    #include <stdio.h>
    #include <math.h>
    #include <assert.h>
    
    
    double factoriel(int n)
    {
      assert (n >= 0);
      ...
    }
    Last edited by Click_here; 02-21-2013 at 06:38 PM.
    Fact - Beethoven wrote his first symphony in C

  9. #9
    SAMARAS std10093's Avatar
    Join Date
    Jan 2011
    Location
    Nice, France
    Posts
    2,694
    But could n go negative? In case input is negative, he passes the absolute value of the number.
    Then, the taylor function passes k as argument. k starts from zero and it is only be increased
    Then inside the function of factorial n is being decreased from a non negative number, until it reaches 0 or 1, and then the recursion starts to rewind.
    Code - functions and small libraries I use


    It’s 2014 and I still use printf() for debugging.


    "Programs must be written for people to read, and only incidentally for machines to execute. " —Harold Abelson

  10. #10
    TEIAM - problem solved
    Join Date
    Apr 2012
    Location
    Melbourne Australia
    Posts
    1,907
    Quote Originally Posted by std10093 View Post
    But could n go negative? In case input is negative, he passes the absolute value of the number.
    Then, the taylor function passes k as argument. k starts from zero and it is only be increased
    Then inside the function of factorial n is being decreased from a non negative number, until it reaches 0 or 1, and then the recursion starts to rewind.
    k is overflowing.
    Fact - Beethoven wrote his first symphony in C

  11. #11
    SAMARAS std10093's Avatar
    Join Date
    Jan 2011
    Location
    Nice, France
    Posts
    2,694
    Oh, I didn't think of that despite I had read your previous post.. Thank you
    Code - functions and small libraries I use


    It’s 2014 and I still use printf() for debugging.


    "Programs must be written for people to read, and only incidentally for machines to execute. " —Harold Abelson

  12. #12
    Registered User
    Join Date
    Nov 2010
    Location
    Long Beach, CA
    Posts
    5,909
    The root of the problem is this:
    Code:
    term= (double)pow(n,k)/factoriel(k) ;
    The largest value a double can hold is roughly 1.7976931348623157 x 10^308.
    Adding the following printf line just below the term = ... line:
    Code:
    printf("n = %d, k = %d, pow(n,k) = %e, fact(k) = %e, term = %e\n",        n, k, pow(n, k), factoriel(k), term);
    Here's what happens when I entered 62:
    Code:
    n = 62, k = 170, pow(n,k) = 5.088470e+304, fact(k) = 7.257416e+306, term = 7.011408e-03
    n = 62, k = 171, pow(n,k) = 3.154851e+306, fact(k) = inf, term = 2.542148e-03
    n = 62, k = 172, pow(n,k) = inf, fact(k) = inf, term = inf
    Woops! pow(62,172) and 172! are too large to fit in a double. You get an result of "inf" or infinity, which borks all the rest of your calculations, including your "break out of the loop" check, hence the infinite loop.

    I would also wager that it is a stack overflow on the recursive call that causes the crash, before k has a chance to overflow. Think, for a 32-bit system, k increments to over 2 billion before overflowing. That means a call to factoriel would have 2 billion instances on the stack. Assuming Intel for this example, you would need 12 bytes (4 for n, 4 for return address, 4 for old base pointer), that's 12*2 billion or more than 24GB of stack space required. I'm guessing you run out of stack long before k hits 2 billion.

    Actually, a quick test, adding this to the top of main:
    Code:
    for (int i = 10000; i < 2000000000; i += 1000) {
        printf("i = %d\n", i);
        factoriel(i);
    }
    Causes the following output:
    Code:
    i = 219000
    Segmentation fault
    Crashed my system somewhere between 218000! and 219000!




    To avoid calculating factorial on a negative number, just use unsigned types.

  13. #13
    Registered User
    Join Date
    Feb 2013
    Posts
    5
    thank you very much guys, i solved the problem after your assistances, i changed the line ;
    Code:
    if(fabs(term<0.0001) < 0.00001)
    with
    Code:
    if(fabs(term<0.0001) < sum/10000)
    by doing this
    it is not stack overflowing , and i do not sacrifice the precision with this,
    and i also saw printf is the best debugger still ) thank you very much

Popular pages Recent additions subscribe to a feed

Similar Threads

  1. Segmentation Fault (core dumped)
    By TimI in forum C Programming
    Replies: 4
    Last Post: 11-05-2012, 07:45 AM
  2. Segmentation fault (core dumped)
    By benjaminp in forum C Programming
    Replies: 8
    Last Post: 10-10-2012, 12:46 PM
  3. Segmentation fault (core dumped)
    By mrbotts in forum C Programming
    Replies: 2
    Last Post: 01-10-2012, 11:06 AM
  4. Segmentation Fault (core dumped)
    By sameer2904 in forum C Programming
    Replies: 3
    Last Post: 01-09-2012, 07:37 AM
  5. Segmentation fault (core dumped)
    By JYSN in forum C Programming
    Replies: 1
    Last Post: 02-21-2002, 03:24 AM

Tags for this Thread