Function Pointer in C

Function Pointer in C Language with Examples

In this article, I will discuss the Function Pointer in C Language with Examples. Please read our previous articles discussing Dangling Pointer in C Language with Examples. Function pointers in C are pointers that point to functions rather than variables. They are powerful, enabling dynamic linking of functions, callbacks, and more complex programming techniques like function dispatch tables. 

Function Pointer in C Language

The pointer variable that holds a function’s address is called a function pointer. The basic advantage of a function pointer is that one function can be passed as a parameter to another function. Function pointer calls are faster than normal functions.

We already discussed that, in C Programming Language, we can create a pointer of any data type such as int, char, float, etc. In C Programming Language, we can also create a pointer pointing to a function. In that case, the code of that function always resides in the memory. That means the function now has some address. We can get the address of memory by using the function pointer.

Example: Function Pointer in C Language

Let us understand the Function Pointer in C Language with an example. In the below sample code, we are simply printing the address of the main and Fun functions.

#include <stdio.h>
int Fun()
{
    int x = 10;
}
int main()
{
    printf ("Address of Main Function : %p", main);
    printf ("\nAddress of Fun Function : %p", Fun);
    return 0;
}
Output: 

Function Pointer in C Language

The above output shows that the main() function and other functions have some addresses. Therefore, we can also conclude that every function has some address.

Declaration of a Function Pointer in C Language:

In the previous example, we conclude that every function has some addresses. So, now, we will see how to create a pointer and how a pointer points to those function addresses.

Syntax of Function Pointer in C Language:
return_type (*ptr_name)(type1, type2…);

Example: int (*IP) (int);
In this example, *IP is a pointer that points to a function that returns an integer value and accepts an integer value as an argument.

Example: float (*FP) (float);
In this example, *FP is a pointer that points to a function that returns a float value and accepts a float value as an argument.

So, here, you can observe that the declaration of a function pointer is similar to the declaration of a function, except that the pointer is preceded by a *. So, in the above two examples, FP and IP are declared as functions rather than pointers.

We have seen only how to declare a function pointer in C Language. Now. we will see how to assign the address of a function to a function pointer in C Programming Language.

How do you assign the address of a function to a function pointer in C?

Let us see how to assign the address of a function to a function pointer in C Language. The most important point you need to remember is that the declaration of a function is necessary before assigning the address of that function to a function pointer. The following three statements describe the declaration of a function, the declaration of a function pointer, and assigning the address of the function to a function pointer.
Declaration of Function: int fun(int , int);
Declaration of a Function Pointer: int (*IP) (int , int);
Assigning the address of fun to the IP pointer: IP = fun;
In the above declarations, the function pointer IP contains the address of the fun function.

How do you call a function through a function pointer?

We already know how to call a function in C Language. Now, we will see how to call a function using a function pointer. Suppose we declare a function as follows:
int fun(int , int);

We can call the above function as follows:
int result = fun(10 , 20);

We can also call the above function using a function pointer as follows:
int result = (*IP)(10, 20); // Calling a function using function pointer.
OR
int result = IP(10,20); // Calling a function using function pointer by removing the indirection operator

Note: If we use a function pointer to call a function in C Language, we can omit the indirection operator as we did in the second case. However, it is recommended to use the indirection operator as it makes it clear to the user that we are using a function pointer.

Program to Understand Function Pointer in C Language:
#include <stdio.h>
int Addition(int, int);
int main()
{
    int a, b;
    int (*IP) (int, int);
    printf ("Enter Two Numbers : ");
    scanf ("%d %d", &a, &b);
    IP = Addition;
    int result = (*IP) (a, b);
    printf ("Result  : %d", result);
    return 0;
}

int Addition(int a, int b)
{
    int c = a + b;
    return c;
}
Output:

Program to Understand Function Pointer in C Language

Passing a function’s address as an argument to another function in C:

It is also possible in C Language that we can pass the address of a function as an argument to other functions in the same way we send other arguments to the function. Let us understand this with an example.

In the below example, we have created two functions, i.e., Function1 and Function2. The Function1 function contains the function pointer as an argument. In the main() method, the Function1 method is called, and we pass the address of Function2. When Function1 is called, the pointer ptr contains the address of the Function2 function. Inside Function1, we call the Function2 method by using the function pointer.

#include <stdio.h>
void Function1(void (*ptr) ());
void Function2();
int main()
{
    Function1(Function2);
    return 0;
}

void Function1(void (*ptr) ())
{
    printf ("Function1 is called");
    (*ptr) ();
}

void Function2()
{
    printf ("\nFunction2 is called");
}
Output:

Passing a function's address as an argument to another function in C

Use Cases of Function Pointers in C:

Function pointers are used in various scenarios in C programming:

  • Callbacks: They allow for implementing callback functions. For example, in libraries or APIs, you need to pass a custom function to be called later.
  • Dynamic Function Calling: They enable calling different functions dynamically at runtime based on certain conditions, which is useful in implementing strategies or state machines.
  • Interface Implementations: Similar to polymorphism in object-oriented languages, function pointers can mimic different behaviors by pointing to different functions.
  • Event Handling: In GUI or event-driven programming, they can be used to handle events like mouse clicks or keypresses.
Example: Passing Function Pointers to Functions

Function pointers can be passed as arguments to other functions. This allows for callback mechanisms.

void greet(void (*greetFunc)(void)) {
    greetFunc(); // Calling the callback function
}

void sayHello() {
    printf("Hello!\n");
}

void sayGoodbye() {
    printf("Goodbye!\n");
}

int main() {
    greet(sayHello);    // Output: Hello!
    greet(sayGoodbye);  // Output: Goodbye!

    return 0;
}
Example: Array of Function Pointers

Function pointers can be stored in arrays to create a table of functions. This is often used in implementing state machines or command parsers.

void option1() { printf("Option 1 selected\n"); }
void option2() { printf("Option 2 selected\n"); }
void option3() { printf("Option 3 selected\n"); }

int main() {
    void (*options[])(void) = {option1, option2, option3};

    // Simulate user input
    int userInput = 1; // User selected option 2

    // Call the selected function
    if(userInput >= 0 && userInput < 3) {
        (*options[userInput])(); // Output: Option 2 selected
    }

    return 0;
}
Example: Using Function Pointers for Comparisons

Function pointers can be useful in generic algorithms, like sorting, where the comparison logic can be passed as a function pointer.

#include <stdlib.h>

int compare(const void *a, const void *b) {
    return (*(int *)a - *(int *)b);
}

int main() {
    int arr[] = {40, 10, 100, 30, 20};
    int n = sizeof(arr) / sizeof(arr[0]);

    qsort(arr, n, sizeof(int), compare);

    for(int i = 0; i < n; i++) {
        printf("%d ", arr[i]);
    }
    // Output: 10 20 30 40 100

    return 0;
}
Event Handling Example Using Function Pointers in C

Event handling using function pointers in C can be a powerful way to create a flexible and modular design. Here’s a basic example of implementing a simple Event Handling system using function pointers.

Scenario: Imagine you’re writing a program that needs to handle different types of events, like keyboard input, mouse clicks, or custom application events. You can define function pointers for each type of event handler and then call the appropriate handler when an event occurs.

Step 1: Define Function Pointer Types

First, we’ll define types for different event handlers. For simplicity, let’s consider two event types: keyboard events and mouse events.

typedef void (*KeyboardEventHandler)(char key);
typedef void (*MouseEventHandler)(int x, int y);
Step 2: Create Event Handlers

Next, let’s implement some event handlers.

void handleKeyPress(char key) {
    printf("Key Pressed: %c\n", key);
}

void handleMouseClick(int x, int y) {
    printf("Mouse Clicked at: (%d, %d)\n", x, y);
}
Step 3: Event Dispatcher

Now, we need a way to dispatch events to the appropriate handlers. We can create a structure that holds function pointers to the event handlers.

struct EventHandlers {
    KeyboardEventHandler keyHandler;
    MouseEventHandler mouseHandler;
};
Step 4: Registering Event Handlers

We’ll need a function to register event handlers.

void registerEventHandlers(struct EventHandlers *handlers, KeyboardEventHandler keyHandler, MouseEventHandler mouseHandler) {
    handlers->keyHandler = keyHandler;
    handlers->mouseHandler = mouseHandler;
}
Step 5: Simulating Events

In a real-world application, events would be triggered by the system or user actions. For this example, we’ll simulate events.

void simulateKeyPress(struct EventHandlers *handlers, char key) {
    if (handlers->keyHandler != NULL) {
        handlers->keyHandler(key);
    }
}

void simulateMouseClick(struct EventHandlers *handlers, int x, int y) {
    if (handlers->mouseHandler != NULL) {
        handlers->mouseHandler(x, y);
    }
}
Step 6: Main Function

Finally, we’ll put everything together in the main function.

int main() {
    struct EventHandlers handlers;

    // Register event handlers
    registerEventHandlers(&handlers, handleKeyPress, handleMouseClick);

    // Simulate some events
    simulateKeyPress(&handlers, 'A');
    simulateMouseClick(&handlers, 100, 200);

    return 0;
}

Output
When you run this program, it simulates a key press and a mouse click event, triggering the appropriate handlers:

Key Pressed: A
Mouse Clicked at: (100, 200)

This example demonstrates a basic Event Handling System using function pointers in C. In a more complex system, you might have a loop that waits for real events from the operating system or user and then dispatches them to the registered handlers. The key benefit of this approach is its flexibility; you can easily swap out event handlers or add new types of events without changing the core event dispatching logic.

In the next article, I will discuss Near, Far, and Huge Pointers in C Language with Examples. In this article, I try to explain the Function Pointer in C Language with Examples. I hope you enjoy this Function Pointer in C Language with Examples article. I would like to have your feedback. Please post your feedback, questions, or comments about this article.

Leave a Reply

Your email address will not be published. Required fields are marked *