3

I have below code running fine and giving out expected result. I have an additional query that how can I declare a pointer in my main function that holds the address of function A(funcA) ?

#include<stdio.h>
#include<stdlib.h>


int funcB (void)
{
 printf("\n Now you are in function B \n ");

 printf ("\n this function is for returning code value no matter what\n");

 return -10;
}

int (*funcA(int x,int y)) (void)
{
 printf( " I am in function A \n ");
   static int sum;
   sum=x+y;
 printf ( "\n Sum is %d ",sum);
 return &funcB;
 }

int main ()

{

int (*fpb)(void);

int x;

fpb=funcA(10,15);

x=(*fpb)();   // Calling function B through fpb pointer

printf("\n Value stored in x for code is %d \n",x);

}

Result :

I am in function A

Sum is 25
Now you are in function B

this function is for returning code value no matter what

Value stored in x for code is -10
2
  • This Below works ,(Its nice to know there are different options for declaring pointer some of them pretty easy now as through auto keyword ). I am declaring fpa pointer pointing to function A. Luckily I found that syntax for fpa and fpb happens to be same. int (*fpa) (void); fpa=funcA(100,200); Commented Mar 28, 2016 at 14:56
  • Don't try to write multi-language source files. That is extremely hard work and any possible advantage versus writing single-language source files (various files rather than one) is very very minimal. Commented Mar 28, 2016 at 15:15

7 Answers 7

4

how can I declare a pointer in my main function that holds the address of function A(funcA) ?

  1. You could write it directly (and uglily):

    int (*(*fpa)(int,int)) (void) = &funcA;

  2. You could use typedef to make it clear:

    typedef int (*FPB)(void);
    typedef FPB (*FPA)(int, int);
    FPA fpa = &funcA;

  3. Because you tagged c++, you could use auto specifier (since c++11) to make it direct and clear:

    auto fpa = &funcA;

Sign up to request clarification or add additional context in comments.

5 Comments

@songyuanyao : I too agree , just to mention that it should be typedef int (FPB) (void);
@theartist33 * is necessary to make it a function pointer type. demo.
@songyuanyao : it could be but w.r.t this original code I did not want funcB to return any address it's simple int (fpb) (void) and I checked its working this way , with declaring it as you said with *funcB as typedef it didn't throw error but run time memory fault
@theartist33 I tried it here. Runtime fault might be other issues.
@theartist33 I see. You're using fa *fpa, it's fine.
3

The syntax is grokky enough that it's best to use a typedef. I'm not assuming C++11. The ()s go around *NameOfType:

typedef int (*funcBTypePointer) (void);

int main ()
{
    funcBTypePointer fpb;

    ...
}

I see that funcA is to return the address of funcB. Here's how to do that:

funcBTypePointer funcA(int x,int y)
{
 printf( " I am in function A \n ");
 static int sum;
 sum=x+y;
 printf ( "\n Sum is %d ",sum);
 return funcB;
}

If you refer to a function without an argument list, you get a pointer to the function; & is not needed.

For more information on function pointers, see this tutorial: http://www.learncpp.com/cpp-tutorial/78-function-pointers/

Comments

2

To figure out the type for a pointer to funcA, take the declaration of funcA:

int (*funcA(int x,int y)) (void)

and replace funcA with (*fptr), so your declaration becomes

int (*(*fptr)(int x, int y))(void);

which reads as

        fptr                          -- fptr
       *fptr                          -- is a pointer
      (*fptr)(            )           -- to a function with
      (*fptr)(    x,      )           -- parameter x
      (*fptr)(int x,      )           --   is an int
      (*fptr)(int x,     y)           -- parameter y
      (*fptr)(int x, int y)           --   is an int
     *(*fptr)(int x, int y)           -- returning a pointer
    (*(*fptr)(int x, int y))(    )    -- to a function with
    (*(*fptr)(int x, int y))(void)    -- no parameters
int (*(*fptr)(int x, int y))(void);   -- returning int

You'd assign it as

fptr = funcA;

and call it as

int x = (*(*fptr)(a,b))();

Note that while some of us1 find this kind of declaration perfectly transparent, most C programmers don't obsess over declaration syntax to this level and prefer to hide most of that complexity behind typedefs:

typedef int fb(void);
typedef fb *fa(int x, int y);

fa *fptr = funcA;

However, that declaration doesn't really tell you how to use fptr in an expression, whereas

int (*(*fptr)(int x, int y))(void);

is pretty unambiguous:

int x = (*(*fptr)(a,b))();


1. I will cheerfully admit I'm an outlier in this regard; I once wrote some code that did pretty much what the fptr call above does (that is, call multiple functions through pointers in a single expression) and thought it was crystal-clear. My coworkers quickly reminded me that I'm weird and insisted I break those into separate statements.

2 Comments

I tried to use below as you wrote above but it's throwing error **too many arguments ** while compiling int (*(*fpa)(int,int))(void)=NULL; int t=(*(*fpa)(10,30))(void); .
@theartist33: Derp. Sorry, I left the void keyword in the function call, which is where the error is coming from; it should be int t = (*(*fpa)(10,30))();. That's what I get for not testing what I write. I'll fix my answer.
1

First rule of declaring "pointers to function" is "use a typedef". You will be grateful when you come back in two weeks time, and try to work out what the hell is going on.

typedef void (*pfuncB_t)();  // (void) is a C-compatability hack.  Use () in C++.

so funcA's declaration becomes a lot easier to read:

pfuncB_t funcA(int x, int y);

... and declaring a type for a pointer to funcA is also easy.

typedef pfuncB_t (*pfuncA_t)(int, int);

and you can use it like:

pfuncA_t globalA = &funcA;   // You don't need the address-of, but it is legal.

Comments

1

How do I declare a pointer that can hold a pointer to funcA?

Unless you're very brave (and I'm too lazy to be that brave), you use a typedef for the pointer to FuncB type:

typedef int (*FunctionReturningInt)(void);

Now, funcA is a function returning a FunctionReturningInt:

extern FunctionReturningInt funcA(int x, int y);

To create a pointer to that:

FunctionReturningInt (*funcA_ptr)(int x, int y) = funcA;

1 Comment

That is the "Yes, Minister" meaning of "brave". See c2.com/cgi/wiki?YesMinisterCourageValue
1

Use a few typedefs

#include <stdio.h>
#include <stdlib.h>

int funcB(void) {
    printf("Now you are in function B\n");
    printf("this function is for returning code value no matter what\n");
    return -10;
}

int (*funcA(int x,int y)) (void) {
    printf("I am in function A\n");
    static int sum;
    sum = x + y;
    printf("Sum is %d\n", sum);
    return &funcB;
}

// typedefs to make life easier    
typedef int (ta)(void);
typedef ta *(tb)(int, int); // use previous typedef'd ta

int main(void) {
    int x, y;
    ta *fpb;
    tb *fpa;

    fpb = funcA(10, 15);
    fpa = funcA;
    x = fpb();   // Calling function B through fpb pointer
    y = fpa(10, 15)(); // calling function B through pointer to function A

    printf("Value stored in x for code is %d\n", x);
    printf("Value stored in y for code is %d\n", y);

    return 0;
}

Comments

1

It is also worth mentioning that you can also use std::function (c++11). However, this is not a function pointer, but rather a wrapper that can hold any callable object. This is a more heavier approach compared to simple pointers.

If function pointers are enough for your case and you don't need to manage a lot of functions then I would definitely recommend to use function pointers.

(http://en.cppreference.com/w/cpp/utility/functional/function)

#include <cstdio>
#include <cstdlib>
#include <functional>


int funcB()
{
  printf("\n Now you are in function B \n ");
  printf("\n this function is for returning code value no matter what\n");
  return -10;
}

std::function<int(void)> funcA(int x, int y)
{
  printf(" I am in function A \n ");
  static int sum;
  sum = x + y;
  printf("\n Sum is %d ", sum);
  return funcB;
}

int main()
{
  std::function<std::function<int(void)>(int, int)> func_a = funcA;
  std::function<int(void)> func_b = func_a(10, 15);
  int x = func_b();

  printf("\n Value stored in x for code is %d \n", x);

  return 0;
}

Comments

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.