Recursion.

Examples given in C but the concept could be extended to other languages.

Basic idea.

At its simplest form, recursion is simply a function calling itself. That is it. When a recursive function calls itself, it is crucial to remember;

i) The new call will start at the beginning of the function.

ii) On returning the function will continue execution from where it left off.

With this knowledge, it is therefore easier to picture recursion as it executes.

When the function calls itself, separate memory from the stack section of memory is given for the new function. If this goes on indefinitely, eventually the program, which the function is a part of, will take up too much memory than is available and the operating system will kill the program or it will cause a segmentation fault. When the stack memory is filled with function calls, it is called a stack overflow error (does that name ring a bell?).

To avoid this, a condition is given when the function will stop calling another function and instead return. This condition is called the base condition. Typically, in recursion problems, this condition is the recursive condition i.e. the basis from which the recursion occurs. For example, in a factorial problem, it is the factorial of 0 or 1. The base condition is crucial since it gives the end of the recursion and enables functions to start returning.

When functions return, their execution ends and if they return a value, they give this value back to the function that called them. This is important since after execution, they are removed from the stack, with the function called last, removed first, all the way to the first function which can then finish executing.

An example of this is a function that prints a string and a newline at the end. (Like the puts function in C but this one does not count the printed characters.)

This function prints, the first character then calls the next function with the next character as its argument till it reaches the null byte, when it prints a newline character and returns the function.

Points to remember.

  1. Each function call will need the same arguments as the calling function.

  2. Each variable in the function will be recreated with each call.

Since each call prints the argument passed to it, the function will print till it gets to the end then come back and fall out of the stack. Knowing it will print the variable as it is passed, the function can be tweaked to print a string in reverse as below,

It can still be tweaked to print a line in reverse and then the right way.(Try this as an exercise).

Both these examples are void functions. Recursion can also be used in functions that return a value, as this square-root function below shows.

Now this function only considers integer square roots, returning -1 otherwise, but it could be tweaked to find other square roots. The function works such that once it finds the root, after iterating through all numbers less than the given number and finding the squares, it returns it. Since no other function modifies the root, the root is returned as it is to the calling function. This function works by setting the base condition to the natural integer root of the number.

Note.

The prime number finder function below uses a similar algorithm but it won't work.

The reason is simple, the argument i++ that is passed is an expression that assigns the increment after execution, not before execution. This means the function will recur indefinitely when it encounters a prime number leading to a stack overflow error or a segmentation fault. A simple fix to the above function is shown below

This is crucial since recursion can be tricky.

A sure way to write good recursive functions is to picture how they call each other and fill the stack and how they will leave the stack after execution.

Recursion can be tricky and difficult to write well. However, just because something is tricky and difficult does not mean we can't or shouldnt do it.

I hope this guides your recursion journey well. Find more examples of recursive functions, well documented, on my GitHub: https://github.com/dedix-7