Function Pointers with typedef - Method 2
In this chapter, you are going to learn
Topics in this section,
Step 1 : Define function type
typedef return_type (* function_type) (parameters_list);
Step 2 : Define function Pointer using function type
function_type fp;
Step 3 : Assing address of a function to
fp
fp = funx;
Step 4 : Call the function using
fp
fp(); // This is equal to funx()
In this program,
Function sum() returns sum of two integers
1#include <stdio.h>
2
3int sum(int a, int b)
4{
5 return a + b;
6}
7
8int main(void)
9{
10 int s;
11
12 s = sum(5, 6);
13
14 printf("sum = %d\n", s);
15
16 return 0;
17}
Now let us replace call to function sum() using function pointer
Step 1 : Define function type
typedef int (*fp)(int, int);
Step 2 : Define function Pointer using function type
fp calc;
Step 3 : Define a function
int sum(int a, int b) { return a + b; }
Note that, return type and function parameters of function pointer should match with that of actual function
Step 4 : Assign function pointer with address of an actual function
calc = sum;
OR
calc = ∑
Step 5 : Use the function pointer to call the function
s = calc(5, 6);
OR
s = (*calc)(5, 6);
See full program below
1#include <stdio.h>
2
3// Step 1 : Define a function pointer type
4typedef int (*fp)(int, int);
5
6// Step 2 : Define function Pointer using function type
7fp calc;
8
9// Step 3 : Define a function
10int sum(int a, int b)
11{
12 return a + b;
13}
14
15int main(void)
16{
17 int s;
18
19 // Step 4 : Assign function pointer with address of an actual function
20 calc = sum;
21
22 // Step 5 : Use the function pointer to call the function
23 s = calc(5, 6);
24
25 printf("sum = %d\n", s);
26
27 return 0;
28}
In this section, you are going to learn
Functions taking function pointers as an arguement
Step 1 : Define a function called
fx()
Step 2 : Identify the function pointer prototype
fp
for above functionStep 3 : Define a function
fy()
taking function pointerfp
as an arguementStep 4 : Call the function
fx()
using function pointerfp
insidefy()
Step 5 : Call the function
fy()
by passingfx
as argumentStep 6 : Let us see few examples
Step 1 : Define a function called
fx()
void fx(void)
{
printf("Inside function fx()\n");
}
Step 2 : Identify the function pointer prototype
fp
for above function
typedef void (*fp)(void);
fp fptr;
Step 3 : Define a function
fy()
taking function pointerfp
as an arguement
void fy(fp fptr)
{
}
Step 4 : Call the function
fx()
using function pointerfp
insidefy()
void fy(fp fptr)
{
fptr();
}
Step 5 : Call the function
fy()
by passingfx
as argument
fy(fx);
See full program below
1#include <stdio.h>
2
3typedef void (*fp)(void);
4
5void fx(void)
6{
7 printf("Inside function fx()\n");
8}
9
10void fy(fp fptr)
11{
12 fptr();
13}
14
15int main(void)
16{
17 fy(fx);
18
19 return 0;
20}
Inside function fx()
Step 1 : Define two functions
sum()
,sub()
int sum(int a, int b)
{
return a + b;
}
int sub(int a, int b)
{
return a - b;
}
Note that, Prototypes of sum() and sub() are matching
Step 2 : Identify the function pointer prototype for functions
sum()
,sub()
typedef int (*fp)(int, int);
fp calc;
In this example,
calc
is the function pointerreturn type of
calc
isint
. Because return type ofsum
andsub
isint
Number of parameters of
calc
is two. Because Number of parameters ofsum
andsub
is twoType of first parameter is
int
. Because type of first parameter isint
insum
andsub
Type of second parameter is
int
. Because type of second parameter isint
insum
andsub
Step 3 : Define a function
do_calculation()
taking function pointercalc
as an arguement
int do_calculation(fp calc, int a, int b)
{
}
do_calculation
takes 3 arguementsFirst is function pointer
calc
Second is integer
a
Third is integer
b
Step 4 : Call the function pointer
calc
insidedo_calculation
int do_calculation(fp calc, int a, int b)
{
return calc(a, b);
}
calc
is a function pointer which can hold the address of any function whose prototype matches with that ofcalc
Step 5 : Call the function
do_calculation()
by passingsum
orsub
as argument
While calling
do_calculation()
, pass 3 arguementsFirst : Address of a function whose prototype matches with that of
calc
Second : integer
Third : integer
See full program below
Function
do_calculation
is called first time to perform addition usingsum
Function
do_calculation
is called second time to perform subtraction usingsub
In both cases, definition of function
do_calculation
is common !
1#include <stdio.h>
2
3typedef int (*fp)(int, int);
4
5int sum(int a, int b)
6{
7 return a + b;
8}
9
10int sub(int a, int b)
11{
12 return a - b;
13}
14
15int do_calculation(fp calc, int a, int b)
16{
17 return calc(a, b);
18}
19
20int main(void)
21{
22 int s;
23
24 s = do_calculation(sum, 5, 6);
25
26 printf("sum = %d\n", s);
27
28 s = do_calculation(sub, 5, 6);
29
30 printf("sub = %d\n", s);
31
32 return 0;
33}
1sum = 11
2sub = -1
In this section, you are going to learn
Functions returning function pointers
Step 1 : Define a function
fx
void fx(void) { printf("Inside function fx()\n"); }
Step 2 : Identify the function pointer prototype for function
fx
typedef void (*fp)(void);
Step 2 : Define a function
get_fx_operation
which returns function pointerfp get_fx_operation(void) { return fx; }
Note the syntax !
Step 3 : Call
get_fx_operation
and store the return value in function pointerfx_p
fx_p = get_fx_operation();
Where the prototype of
fx_p
should match with prototype offx()
fp fx_p;
Step 4 : Call the function using
fx_p
fx_p(); // This calls function fx()
Step 5 : See the full program below
1#include <stdio.h>
2
3typedef void (*fp)(void);
4
5void fx(void)
6{
7 printf("Inside function fx()\n");
8}
9
10fp get_fx_operation(void)
11{
12 return fx;
13}
14
15int main(void)
16{
17 fp fx_p;
18
19 fx_p = get_fx_operation();
20
21 fx_p(); // This calls function fx()
22
23 return 0;
24}
In this example, program decides the sorting mechanism to be used at run time based on the array size
Step 1 : Define two sorting algorithm functions
void insertion_sort(int *arr, int n)
{
}
void selection_sort(int *arr, int n)
{
}
Step 2 : Define function pointer type for above functions
typedef void (*sort_fp)(int *arr, int n)
Step 3 :
get_sort_method
returns sorting method to be used based on array size
sort_fp get_sort_method(int n)
{
if (n <= 2)
return insertion_sort;
else
return selection_sort;
}
Step 4 :
analyse_data
callsget_sort_method
function to sort
void analyse_data(int *arr, int n)
{
sort_fp sort_fptr;
sort_fptr = get_sort_method(n);
sort_fptr(arr, n);
}
Step 5 : What is the advantage ?
Whenever the array size changes the function
analyse_data
need not change !If
analyse_data
is defined in a sepratex.c
file, we need not recompilex.c
In real time,
analyse_data
can be very big function with calls to many function pointers
Step 4 : See the full program below
1#include <stdio.h>
2
3typedef void (*sort_fp)(int *arr, int n);
4
5int arr[] = { 47, 13, 63, 29, 7 };
6
7void insertion_sort(int *arr, int n)
8{
9}
10
11void selection_sort(int *arr, int n)
12{
13}
14
15sort_fp get_sort_method(int n)
16{
17 if (n <= 2)
18 return insertion_sort;
19 else
20 return selection_sort;
21}
22
23void analyse_data(int *arr, int n)
24{
25 sort_fp sort_fptr;
26
27 sort_fptr = get_sort_method(n);
28
29 sort_fptr(arr, n);
30}
31
32int main(void)
33{
34 analyse_data(arr, sizeof(arr) / sizeof(arr[0]) );
35
36 return 0;
37}
Step 1 : Define a function pointer type
fp
typedef void (*fp_param)(int); typedef void (*fp_return)(void);
Step 1 : Define a function
get_fx_operation
which takes function pointer as arguement and returns a function pointerget_fx_operation
is written using concepts from Example 2 and Example 3get_fx_operation
takesfs_p
as arguement which is a function pointer which can hold the address of a function which returnsvoid
and takesint
as an arguementget_fx_operation
returnsfx
orgx
depending on the value ofa
fp_return get_fx_operation( fp_param fs_p )
{
int a = 5;
fs_p(a);
if (a > 0)
return fx;
else
return gx;
}
Step 2 : Call
get_fx_operation
and pass address of a functionWe are passing address of
sample_fun
as arguement toget_fx_operation
fx_p = get_fx_operation(sample_fun);
Step 3 : See the full program below
1#include <stdio.h>
2
3typedef void (*fp_param)(int);
4
5typedef void (*fp_return)(void);
6
7void fx(void)
8{
9 printf("Inside function fx() : Positive\n");
10}
11
12void gx(void)
13{
14 printf("Inside function gx() : Negative\n");
15}
16
17void sample_fun(int a)
18{
19 printf("a = %d \n", a);
20}
21
22fp_return get_fx_operation( fp_param fs_p )
23{
24 int a = 5;
25
26 fs_p(a);
27
28 if (a > 0)
29 return fx;
30 else
31 return gx;
32}
33
34int main(void)
35{
36 fp_return fx_p;
37
38 fx_p = get_fx_operation(sample_fun);
39
40 fx_p(); // This calls function fx()
41
42 return 0;
43}
Similar functions can be grouped into an array
We call this as array of function pointers
Array of function pointers enables asynchronous event handling
typedef return_type (*function_ptr_type) (parameters_list);
function_ptr_type fp_arr[] = {functions_list};
Step 1 : Define an array of function pointers
calc
is an array of function pointersEach element in this array is a function which takes two integers as argement and returns void
typedef void (*fp)(int, int);
fp calc[] = { sum, sub, mul };
Step 2 : Find number of elements in an array generic way
Number of elements in Array = Sizeof_Array / Size of One element
Number of elements in calc
= sizeof(calc) / sizeof(calc[0])
Step 3 : Call the functions using array of function pointers
calc[i](5, 6);
// calc[0](5, 6) equals sum(5, 6)
// calc[1](5, 6) equals sub(5, 6)
// calc[2](5, 6) equals mul(5, 6)
Step 4 : See full program below
1#include <stdio.h>
2
3void sum(int a, int b)
4{
5 printf("Function sum called : a = %d, b = %d, sum = %d\n", a, b, a + b);
6}
7
8void sub(int a, int b)
9{
10 printf("Function sub called : a = %d, b = %d, sub = %d\n", a, b, a - b);
11}
12
13void mul(int a, int b)
14{
15 printf("Function mul called : a = %d, b = %d, mul = %d\n", a, b, a * b);
16}
17
18typedef void (*fp)(int, int);
19
20fp calc[] = { sum, sub, mul };
21
22int main(void)
23{
24 for (int i = 0; i < sizeof(calc)/sizeof(calc[0]); i++)
25 {
26 calc[i](5, 6);
27 }
28
29 return 0;
30}
Output is as below
Function sum called : a = 5, b = 6, sum = 11
Function sub called : a = 5, b = 6, sub = -1
Function mul called : a = 5, b = 6, mul = 30
Asynchoronous events - Can arrive at any time
In below example, events are generated randomly and handled dynamically
Step 1 : Define functions which handle specific events
void ev_connect_cb(void)
{
printf("Handled ev_connect_cb\n");
}
void ev_disconnect_cb(void)
{
printf("Handled ev_disconnect_cb\n");
}
void ev_reconnect_cb(void)
{
printf("Handled ev_reconnect_cb\n");
}
Step 2 : Map these functions to array of function pointers
typedef void (*fp)(void);
fp ev_cb[] = {
ev_connect_cb,
ev_disconnect_cb,
ev_reconnect_cb,
};
Step 3 : Call these functions based on event generated
ev_cb[ev_id]();
Step 4 : See full program below
1#include <stdio.h>
2#include <stdlib.h>
3#include <time.h>
4#include <unistd.h>
5
6void handle_event(int ev_id);
7
8enum events
9{
10 EV_INIT,
11 EV_CONNECT = EV_INIT,
12 EV_DISCONNECT,
13 EV_RECONNECT,
14 EV_MAX = EV_RECONNECT
15};
16
17void ev_connect_cb(void)
18{
19 printf("Handled ev_connect_cb\n");
20}
21
22void ev_disconnect_cb(void)
23{
24 printf("Handled ev_disconnect_cb\n");
25}
26
27void ev_reconnect_cb(void)
28{
29 printf("Handled ev_reconnect_cb\n");
30}
31
32typedef void (*fp)(void);
33
34fp ev_cb[] = {
35 ev_connect_cb,
36 ev_disconnect_cb,
37 ev_reconnect_cb,
38 };
39
40void generate_events()
41{
42 int i;
43 for (;;) {
44 for (i = 0; i < EV_MAX; i++) {
45 int ev_id = (rand() %
46 (EV_MAX - EV_INIT + 1)) + EV_INIT;
47 handle_event(ev_id);
48 }
49 }
50}
51
52void handle_event(int ev_id)
53{
54 ev_cb[ev_id]();
55}
56
57int main(void)
58{
59 generate_events();
60 return 0;
61}
C language allows programmer to define function pointers inside a structure
After all, function pointer is another variable
Step 1 : Declare function pointers inside a structure
typedef int (*fp)(struct student_db *s);
struct student_db
{
int id;
int age;
int marks;
char name[32];
fp get_age_p;
fp get_marks_p;
};
get_age_p
is a function pointer
get_marks_p
is a function pointer
Step 2 : Assign function pointers with actual function definitions at the time of structure object creation
struct student_db s1 = {
.id = 101,
.age = 20,
.marks = 97,
.name = "Adam",
.get_age_p = get_age,
.get_marks_p = get_marks
};
Step 3 : Call the function via function pointers using structure object
s1.get_age_p(&s1);
Step 4 : See full program below
1#include <stdio.h>
2
3struct student_db;
4
5typedef int (*fp)(struct student_db *s);
6
7struct student_db
8{
9 int id;
10 int age;
11 int marks;
12 char name[32];
13
14 fp get_age_p;
15 fp get_marks_p;
16};
17
18int get_age(struct student_db *s)
19{
20 return s->age;
21}
22
23int get_marks(struct student_db *s)
24{
25 return s->marks;
26}
27
28int main(void)
29{
30 struct student_db s1 = {
31 .id = 101,
32 .age = 20,
33 .marks = 97,
34 .name = "Adam",
35 .get_age_p = get_age,
36 .get_marks_p = get_marks
37 };
38
39 struct student_db s2 = {
40 .id = 102,
41 .age = 21,
42 .marks = 98,
43 .name = "Ram",
44 .get_age_p = get_age,
45 .get_marks_p = get_marks
46 };
47
48 printf("Age of s1 = %d\n", s1.get_age_p(&s1));
49 printf("Marks of s1 = %d\n", s1.get_marks_p(&s1));
50
51 printf("Age of s2 = %d\n", s2.get_age_p(&s2));
52 printf("Marks of s2 = %d\n", s2.get_marks_p(&s2));
53
54 return 0;
55}
Simple function Pointer : Method 1 |
|
---|---|
typedef return_type (*fun) (parameter_list); |
Basic Function Pointer syntax |
fun fp; |
|
fp = function; |
|
fp(); |
|
Simple function Pointer : Method 2 |
|
---|---|
typedef return_type (*fun) (parameter_list); |
Basic Function Pointer syntax |
fun fp; |
|
fp = &function; |
fp` is assigned with address of |
(*fp) (); |
|
Array of function Pointers |
|
---|---|
typedef return_type (*fun) (parameter_list); |
Basic Array of Function Pointers syntax |
fun fp[]; |
|
fp[0] = funx, fp[1] = funy |
function pointers fp[0] and fp[1] are initialised |
fp[0]() |
|
fp[1]() |
|
Current Module
Previous Module
Next Module
Other Modules