Recursive Functions
This document covers recursion in C.
Recursion is a powerful concept in programming where a function calls itself to solve a problem. In C, recursion is used for problems that can be broken down into smaller subproblems, making the code more elegant and easier to understand.
In this section, we will cover:
- What recursion is and how it works.
- Base case and recursive case.
- Examples of recursion (Factorial, Fibonacci, and Binary Search).
- Pros and cons of recursion.
- Common pitfalls, including stack overflow.
How Recursion Works​
A recursive function is a function that calls itself with modified parameters until a stopping condition (base case) is met.
Structure of a Recursive Function​
A recursive function consists of two parts:
- Base Case – Defines when the recursion should stop.
- Recursive Case – Calls itself with modified arguments.
Example​
#include <stdio.h>
void countdown(int n) {
    if (n == 0) { // Base case
        printf("Blast off!\n");
        return;
    }
    printf("%d\n", n);
    countdown(n - 1); // Recursive call
}
int main() {
    countdown(5);
    return 0;
}
- 
Base case: Stops when n == 0. 
- 
Recursive case: Calls countdown(n - 1). 
Examples of Recursive Functions​
Factorial Calculation​
Factorial of n is defined as n! = n × (n-1)!
#include <stdio.h>
int factorial(int n) {
    if (n == 0) return 1; // Base case
    return n * factorial(n - 1); // Recursive case
}
int main() {
    int num = 5;
    printf("Factorial of %d is %d\n", num, factorial(num));
    return 0;
}
Fibonacci Series​
Each Fibonacci number is the sum of the two preceding numbers.
#include <stdio.h>
int fibonacci(int n) {
    if (n == 0) return 0; // Base case
    if (n == 1) return 1; // Base case
    return fibonacci(n - 1) + fibonacci(n - 2); // Recursive case
}
int main() {
    int num = 6;
    printf("Fibonacci(%d) = %d\n", num, fibonacci(num));
    return 0;
}
Binary Search (Recursive Implementation)​
Binary search efficiently finds an element in a sorted array by repeatedly dividing the search range in half.
#include <stdio.h>
int binarySearch(int arr[], int low, int high, int key) {
    if (low > high) return -1; // Base case: Element not found
    
    int mid = low + (high - low) / 2;
    if (arr[mid] == key) return mid;
    else if (arr[mid] > key) return binarySearch(arr, low, mid - 1, key);
    else return binarySearch(arr, mid + 1, high, key);
}
int main() {
    int arr[] = {1, 3, 5, 7, 9, 11};
    int size = sizeof(arr) / sizeof(arr[0]);
    int key = 5;
    int index = binarySearch(arr, 0, size - 1, key);
    if (index != -1) printf("Element found at index %d\n", index);
    else printf("Element not found\n");
    return 0;
}
Advantages and Disadvantages of Recursion​
Advantages​
- Makes complex problems easier to understand.
- Reduces code duplication by using a cleaner, more modular approach.
- Natural fit for problems that can be broken down into smaller subproblems.
Disadvantages​
- Recursion can be inefficient due to repeated function calls.
- May cause stack overflow if the recursion depth is too large.
- Uses more memory compared to iteration.
Common Pitfalls and Stack Overflow​
Missing Base Case​
If a recursive function does not have a proper base case, it will continue calling itself indefinitely, causing a stack overflow.
void infiniteRecursion() {
    printf("This will never stop!\n");
    infiniteRecursion(); // No base case!
}
Solution​
Always define a base case to stop recursion.
Excessive Function Calls (Inefficient Recursion)​
Some recursive functions, like the naive Fibonacci implementation, recompute values multiple times.