This question already has answers here:
typedef int (*pf) needs explaining
(5 answers)
Closed 8 years ago.
I came across this kind of a declaration.
typedef int (*func) (int,int,int);
What is the meaning and use of this?
It defines func as type for function which accepts 3 integers and returns integer.
This is helpful when you pass functions as callbacks or put function addresses into arrays or something like that.
That's the typedef'd name. It reads as: func is a pointer to a function that takes three ints and returns an int.
You can see more on this link
It defines a type func which is a pointer to a function returning an int and taking 3 int arguments.
An example of using this would be:
typedef int (*func) (int, int, int);
int foo(int a, int b, int c) {
return a + b * c;
}
...
// Declare a variable of type func and make it point to foo.
// Note that the "address of" operator (&) can be omitted when taking the
// address of a function.
func f = foo;
// This will call foo with the arguments 2, 3, 4
f(2, 3, 4);
A more realistic scenario might be having a bunch of functions that have the same return type and taking the same type/number of arguments, and you want to call different functions based on the value of some variable. Instead of having a bunch of if-statements or a large switch/case you could place the function pointers in an array and use an index to call the appropriate function.
Related
Normally, when declaring some variable, you put its type before it, like:
int a;
a function pointer may have type like: int(*)(int,int), in case we point to a function that takes two integers and returns an integer. But, when declaring such a pointer, its identifier is not after the type, like:
int(*)(int,int) mypointer;
instead, you must write the identifier in the middle:
int(*mypointer)(int,int);
why is this so?
I explain this in my answer to Why was the C syntax for arrays, pointers, and functions designed this way?, and it basically comes down to:
the language authors preferred to make the syntax variable-centric rather than type-centric. That is, they wanted a programmer to look at the declaration and think "if I write the expression *func(arg), that'll result in an int; if I write *arg[N] I'll have a float" rather than "func must be a pointer to a function taking this and returning that".
The C entry on Wikipedia claims that:
Ritchie's idea was to declare identifiers in contexts resembling their use: "declaration reflects use".
...citing p122 of K&R2.
This structure reflects how a normal function is declared (and used).
Consider a normal function definition:
int foo (int bar, int baz, int quux);
Now consider defining a function pointer to a function of the same signature:
int (*foo) (int, int, int);
Notice how the two structures mirror each other? That makes *foo much easier to identify as a function pointer rather than as something else.
If you're dealing with a function (not a pointer to one), the name is in the middle too. It goes like: return-type function-name "(" argument-list ")" .... For example, in int foo(int), int is the return type, foo the name and int the argument list.
A pointer to a function works pretty much the same way -- return type, then name, then argument list. In this case, we have to add a * to make it a pointer, and (since the * for a pointer is prefix) a pair of parentheses to bind the * to the name instead of the return type. For example, int *foo(int) would mean a function named foo that takes an int parameter and returns a pointer to an int. To get the * bound to foo instead, we need parentheses, giving int (*foo)(int).
This gets particularly ugly when you need an array of pointers to functions. In such a case, most people find it easiest to use a typedef for the pointer type, then create an array of that type:
typedef int (*fptr)(int);
fptr array[10];
I had seen at some places function pointers declared as
int (*foo) (int a, int b);
and at some places a and b are not mentioned and both still works.
so
int (*foo) (int, int)
is also correct.
A very simple way that I found to remember is as mentioned below:
Suppose function is declared as:
int function (int a , int b);
Step1: Simply put function in parentheses:
int (function) (int a , int b);
Step2: Place a * in front of function name and change the name:
int (*funcPntr) (int a , int b);
PS: I am not following proper coding guidelines for naming convention etc. in this answer.
How (*ptr_fun1)(10) and ptr_fun1(10) are same in the below code
Code:
#include<stdio.h>
void fun1(int a)
{
printf("It is %d\n",a);
}
int main()
{
void (*ptr_fun1)(int);
ptr_fun1 = fun1;
/*
ex-
ptr_fun1 fun1
+----+ +-----+
+1000+ +code +
+----+ +-----+
1234 1000
fun1(10); <=> ptr_fun1(10); //how
*/
printf("%d\n%d",ptr_fun1(10),(*ptr_fun1)(20));
return 0;
}
output
10
20
Can some one please explain how it works.
The syntax for declaring (and using) function pointers in C (and C++) is one of the most puzzling aspects of the language for beginners. I shall try to explain a little, here.
First, let's consider pointers to 'simple' types (we'll take the 'int' type as an example). In this case, declaring a variable of the type is trivial: int N; Also, declaring a pointer to an int is also trivial: int *pN;We can interpret this second declaration in terms of 'evaluating' the '*' operator, which means "get the object that resides at the given address." So, in int *pN we are declaring that "the object that lies at the address "pN" is an int.
For functions, this is not so simple! Take a case of a function that takes an int as its (only) argument and returns an int value: int IFunc(int arg);. This is also very straightforward.
But how could we declare a pointer to such a function? We cannot simply apply the same logic as for the 'simple' types (by preceding with a * operator), like this:
int *pIFunc(int arg);
Because this would declare a function that takes an int arg and returns a pointer to an int.
So, the early implementors of the C language had to come up with something better - and completely unambiguous. So they decided to use the syntax of putting the "*NAME" section in parentheses, to isolate that 'dereference' operation from the function's definition:
int (*pIFunc)(int arg);
So, when faced with anything that looks remotely like this: < typename > (*Name1)(...); (where < typename > is any allowable C-type, like int, void, double, or even 'compound' types such as int*, and the "..." inside the second set of brackets can be either empty or a list of other 'types'), recognize it as a declaration of a function pointer (or as dereferencing a function pointer). To get the underlying function 'signature' (or invocation), just remove the first set of brackets and the contained *. So, for:
(*ptr_fun1)(20)
you can read:
ptr_fun1(20)
And, for:
void (*ptr_fun1)(int);
you can see that ptr_fun has the following signature:
void ptr_fun1(int);
I hope this makes things a bit clearer. Feel free to ask for further clarification and/or explanations.
This question already has answers here:
How do function pointers in C work?
(12 answers)
Closed 9 years ago.
In a book, I came across the following question.
The problem which I am facing is, what is a function pointer? How does it work and what is the syntax for it's declaration.
Point the error in given code.
main()
{
int (*p)()=fun;
(*p)();
}
fun()
{
printf("Hi..");
}
my first question is, What does following code snipet signifies?
int (*p)()=fun;
(*p)();
and second obvious question what is the error in the given code..??
refer to ionela.voinescu's answer for solution.. it is same as that written in solution manual..thnx
int (*p)() = fun declares a pointer to a function that returns int, then assigns the address of the function fun to that pointer. (*p)() calls whatever function p is pointing to.
Problems with your code:
fun and main should have a return type. Your compiler might not demand it and assume they return ints, but you should give them one nonetheless.
You need to declare fun above main, or use a prototype
Also, (*p)() is unnecessary; you can just use p().
As a side note, because function pointer syntax is relatively ugly, it's fairly common to see typedefs such as
typedef int(*IntFunc)();
which would allow you to declare and use p like so:
IntFunc p = fun;
p();
The correct code is the following:
#include <stdio.h>
int fun();
int main(){
int (*p)()=fun;
(*p)();
return 0;
}
int fun(){
printf("Hi..");
return 0;
}
1.
int fun();
You have to declare your function before using it in main; Otherwise main wont recognize it.
2.
int (*p)() : Declaration of a variable p which is a pointer to a function that returns int and has no arguments(or undefined number of arguments, depending on the standard).
3.
int fun();
.........
int (*p)()=fun;
In order for this to work fun must also return int. Meaning when assigning a value to a variable this must have a type which corresponds with the declaration of the variable. When assigning a value to a pointer to a function that returns int and has no arguments the function assigned to it must also return int and have no arguments (or undefined number of arguments, depending on the standard).
4.
(*p)();
You call the function p which now points to fun.
fun is name of the the function itself.
int (*p)()
is the definition of the function pointer like 'int a' is the definition of an integer.
int * is the pointer itself, () means it is a pointer to a function.
(*p)();
This is the execution of the function of the function pointer p, i.e. p is assigned to the function fun, which is executed by calling the content of the pointer p, thus (*p)();
This question already has answers here:
what does it mean to convert int to void* or vice versa?
(6 answers)
Closed 9 years ago.
#include <stdio.h>
void pass(void* );
int main()
{
int x;
x = 10;
pass((void*)x);
return 0;
}
void pass(void* x)
{
int y = (int)x;
printf("%d\n", y);
}
output: 10
my questions from the above code..
what happens when we typecast normal variable to void* or any pointer variable?
We have to pass address of the variable to the function because in function definition argument is pointer variable. But this code pass the normal variable ..
This format is followed in linux pthread programming... I am an entry level C programmer. I am compiling this program in linux gcc compiler..
I'm only guessing here, but I think what you are supposed to do is actually pass the address of the variable to the function. You use the address-of operator & to do that
int x = 10;
void *pointer = &x;
And in the function you get the value of the pointer by using the dereference operator *:
int y = *((int *) pointer);
Please read why glib provide macros for this kind of conversions, there's no need to repeat the text here. The main point is: a pointer has a platform dependent size.
If you are planning to use pthreads and you are planning to pass the pass function to pthread_create, you have to malloc/free the arguments you are planning to use (even if the threaded function just need a single int).
Using an integer address (like &x) is probably wrong, indeed each modification you will execute on x will affect the pass behaviour.
This question already has answers here:
passing variable number of arguments
(5 answers)
Closed 9 years ago.
I'm creating a function is necessary pass at least 2 (two) parameters: myStruct and value, the other arguments are optional.
This is a sample of my function:
int find(struct myStruct *, void * value, ...);
This is all arguments possible:
struct myStruct *, void * value, int (*comparable) (void *, void *), int flag
I believe i will have to use va_list, but i would not want of pass null how last parameters. This is possible?
with variable arguments you have at least the following options:
the last parameter is NULL (or something different which is recognizable as terminator)
the "first" parameter is the number of parameters which the function has to recognize.
the first parameter(s) spezify, what has to follow (like format-strings)
but keep in mind: YOU (the programmer) has to ensure, that you provide the right number of parameters. So if you want to make an interface (for other programmers) out of your function, be sure, that it is as failsafe and as naturally as possible. If it is, f.e. a multiple-create-GUI-Function, a NULL-termination list of gui-elements springs in mind.