Thread: Recursive Function Pointer

  1. #1
    Registered User
    Join Date
    Sep 2001
    Posts
    752

    Recursive Function Pointer

    How do I define a type for a function which returns a pointer to its own type?

    That is... how do I typedef fn_type below?
    Code:
    fn_type * fn_ptr = start_function;
    while (fn_ptr != NULL) {
       fn_ptr = fn_ptr();
    }
    C++ extensions are fine to use if need be, and welcome if they make life easier for this problem.
    Last edited by QuestionC; 06-13-2007 at 08:47 AM.
    Callou collei we'll code the way
    Of prime numbers and pings!

  2. #2
    Deathray Engineer MacGyver's Avatar
    Join Date
    Mar 2007
    Posts
    3,210
    So you want a pointer to a function that returns this same type (ie. same pointer to a function)?

    Are you sure you can't think of some easier method to achieve your goal?

  3. #3
    Just Lurking Dave_Sinkula's Avatar
    Join Date
    Oct 2002
    Posts
    5,005
    7. It is easier to write an incorrect program than understand a correct one.
    40. There are two ways to write error-free programs; only the third one works.*

  4. #4
    root koodoo's Avatar
    Join Date
    Oct 2005
    Location
    a small village faraway in the mountains
    Posts
    28
    I went to the link http://c-faq.com/decl/recurfuncp.html and tried to understand it.
    I have a few questions:

    Code:
    int (*funcptr)();	  
    states that funcptr is a pointer to a function that takes no arguments and returns an int.
    
    typedef int (*funcptr)();	  
    does this define funcptr as a type? (this is what I think so, but I haven't used typedef like this before )
    
    again
    funcptr (*ptrfuncptr)();  
    states that ptrfuncptr is a pointer to a function that takes no arguments and returns a funcptr.
    
    typedef funcptr (*ptrfuncptr)();  
    same as before : does this define ptrfuncptr as a type?
    I've written the following code, and at least it works :
    Code:
    #include <stdio.h>
    
    typedef int (*funcptr)();	  /* generic function pointer */
    typedef funcptr (*ptrfuncptr)();  /* ptr to fcn returning g.f.p. */
    
    int main()
    {
    
    funcptr start_function();
    ptrfuncptr state = start_function;
    
    while (state != NULL)
    	state = (ptrfuncptr)(*state)();
    
    
    return 0;
    }
    
    funcptr start_function()
    {
    
    static int i=0;
    ++i;
    
    printf("\nIn function \"start funtion\" for the &#37;dth time!", i);
    
    if(i==5)
    	return NULL;
    else
    	return start_function;
    
    }
    Here the function start-function is being called again and again, (the function itself supplies it's own address) though not recursively, which is obviously not possible as it supplies a pointer to itself in the return statement.

    Looking for some comments.
    Thanks.

    regards,
    koodoo.
    If this helped you, please take the time to rate the value of this post by clicking here.

    Statutory Warning : Beware of C... it's highly addictive.

    --------------------------------------------------------------
    Registered Linux User #388419
    --------------------------------------------------------------

  5. #5
    Officially An Architect brewbuck's Avatar
    Join Date
    Mar 2007
    Location
    Portland, OR
    Posts
    7,396
    Having the function return a void * is probably the best method. The following is valid (in C, but it wouldn't be in C++) and and least with my compiler, is free of warnings:

    Code:
    #include <stdio.h>
    #include <stdlib.h>
    
    typedef void *(*rfunc)(void);
    
    void *func1();
    void *func2();
    void *func3();
    
    void *func1()
    {
       printf("func1()\n");
       return func2;
    }
    
    void *func2()
    {
       printf("func2()\n");
       return func3;
    }
    
    void *func3()
    {
       printf("func3()\n");
       return NULL;
    }
    
    int main()
    {
       rfunc f = func1;
       while(f)
       {
          f = f();
       }
       return 0;
    }

  6. #6
    Officially An Architect brewbuck's Avatar
    Join Date
    Mar 2007
    Location
    Portland, OR
    Posts
    7,396
    Quote Originally Posted by QuestionC View Post
    C++ extensions are fine to use if need be, and welcome if they make life easier for this problem.
    I hadn't noticed this originally. If you're willing to use a little C++, your problem is easily solved by creating a base class with a virtual function (call it "doIt()" or whatever) that returns a pointer to that same base class. Then you can derive various classes from the base and put whatever you want in their doIt() methods. Then you could just call polymorphically through the base class.

    I'd post code, but since this is the C board that's as far as I'll go at the moment.

  7. #7
    Lurking whiteflags's Avatar
    Join Date
    Apr 2006
    Location
    United States
    Posts
    9,612
    Here the function start-function is being called again and again, (the function itself supplies it's own address) though not recursively, which is obviously not possible as it supplies a pointer to itself in the return statement.
    Well it certainly is possible. We can assume that a function always has the same address throughout the program, and since the address is returned by the called function it can be assigned and dereferenced in a while statement. What's written in cases like these is not really recursive because the function completes a step every time as opposed to calling itself and bottoming out, but as stated by the article: in coding a truly recursive solution the function pointers cannot act like real functions because their type compounds with every call.

  8. #8
    Officially An Architect brewbuck's Avatar
    Join Date
    Mar 2007
    Location
    Portland, OR
    Posts
    7,396
    Quote Originally Posted by citizen View Post
    Well it certainly is possible. We can assume that a function always has the same address throughout the program, and since the address is returned by the called function it can be assigned and dereferenced in a while statement. What's written in cases like these is not really recursive because the function completes a step every time as opposed to calling itself and bottoming out, but as stated by the article: in coding a truly recursive solution the function pointers cannot act like real functions because their type compounds with every call.
    I think in this case the word "recursive" is applying to the type (a recursively defined type), not the particular function call pattern.

  9. #9
    Just Lurking Dave_Sinkula's Avatar
    Join Date
    Oct 2002
    Posts
    5,005
    Quote Originally Posted by brewbuck View Post
    Having the function return a void * is probably the best method.
    That's debatable.
    main.c: In function `func1':
    main.c:13: warning: ISO C forbids return between function pointer and `void *'
    main.c: In function `func2':
    main.c:19: warning: ISO C forbids return between function pointer and `void *'
    main.c: In function `main':
    main.c:33: warning: ISO C forbids assignment between function pointer and `void *'
    7. It is easier to write an incorrect program than understand a correct one.
    40. There are two ways to write error-free programs; only the third one works.*

Popular pages Recent additions subscribe to a feed

Similar Threads

  1. sorting number
    By Leslie in forum C Programming
    Replies: 8
    Last Post: 05-20-2009, 04:23 AM
  2. Getting an error with OpenGL: collect2: ld returned 1 exit status
    By Lorgon Jortle in forum C++ Programming
    Replies: 6
    Last Post: 05-08-2009, 08:18 PM
  3. Replies: 5
    Last Post: 04-04-2009, 03:45 AM
  4. Compiler "Warnings"
    By Jeremy G in forum A Brief History of Cprogramming.com
    Replies: 24
    Last Post: 04-24-2005, 01:09 PM
  5. Quick question about SIGSEGV
    By Cikotic in forum C Programming
    Replies: 30
    Last Post: 07-01-2004, 07:48 PM