Mutual Recursion with example of Hofstadter Female and Male sequences
Last Updated :
17 Nov, 2022
Mutual recursion is a variation recursion. Two functions are called mutually recursive if the first function makes a recursive call to the second function and the second function, in turn, calls the first one.
In software development, this concept is used in circular dependency which is a relation between two or more modules which either directly or indirectly depend on each other to function properly. Such modules are also known as mutually recursive.
A great example of mutual recursion would be implementing the Hofstadter Sequence.
Hofstadter Sequence
In mathematics, a Hofstadter sequence is a member of a family of related integer sequences defined by non-linear recurrence relations. In this example we are going to focus on Hofstadter Female and Male sequences:
F ( 0 ) = 1M ( 0 ) = 0 F ( n ) = n - M ( F ( n - 1 ) ), n > 0 M ( n ) = n - F ( M ( n - 1 ) ), n > 0.
C++
// C++ program to implement Hofstadter Sequence
// using mutual recursion
#include <bits/stdc++.h>
using namespace std;
int hofstadterFemale(int);
int hofstadterMale(int);
// Female function
int hofstadterFemale(int n)
{
if (n < 0)
return 0;
else
if (n == 0)
return 1;
else
return (n - hofstadterFemale(n - 1));
}
// Male function
int hofstadterMale(int n)
{
if (n < 0)
return 0;
else
if (n == 0)
return 0;
else
return (n - hofstadterMale(n - 1));
}
// Driver Code
int main()
{
int i;
cout << "F: ";
for (i = 0; i < 20; i++)
cout << hofstadterFemale(i) << " ";
cout << "\n";
cout << "M: ";
for (i = 0; i < 20; i++)
cout << hofstadterMale(i)<< " ";
return 0;
}
// This code is contributed by shubhamsingh10
C
// C program to implement Hofstader Sequence
// using mutual recursion
#include <stdio.h>
int hofstaderFemale(int);
int hofstaderMale(int);
// Female function
int hofstaderFemale(int n)
{
if (n < 0)
return;
else
return (n == 0) ? 1 : n - hofstaderFemale(n - 1);
}
// Male function
int hofstaderMale(int n)
{
if (n < 0)
return;
else
return (n == 0) ? 0 : n - hofstaderMale(n - 1);
}
// hard coded driver function to run the program
int main()
{
int i;
printf("F: ");
for (i = 0; i < 20; i++)
printf("%d ", hofstaderFemale(i));
printf("\n");
printf("M: ");
for (i = 0; i < 20; i++)
printf("%d ", hofstaderMale(i));
return 0;
}
Java
// Java program to implement Hofstader
// Sequence using mutual recursion
import java .io.*;
class GFG {
// Female function
static int hofstaderFemale(int n)
{
if (n < 0)
return 0;
else
return (n == 0) ? 1 : n -
hofstaderFemale(n - 1);
}
// Male function
static int hofstaderMale(int n)
{
if (n < 0)
return 0;
else
return (n == 0) ? 0 : n -
hofstaderMale(n - 1);
}
// Driver Code
static public void main (String[] args)
{
int i;
System.out.print("F: ");
for (i = 0; i < 20; i++)
System.out.print(hofstaderFemale(i)
+ " ");
System.out.println();
System.out.print("M: ");
for (i = 0; i < 20; i++)
System.out.print(hofstaderMale(i)
+ " ");
}
}
// This code is contributed by anuj_67.
Python3
# Python program to implement
# Hofstader Sequence using
# mutual recursion
# Female function
def hofstaderFemale(n):
if n < 0:
return;
else:
val = 1 if n == 0 else (
n - hofstaderFemale(n - 1))
return val
# Male function
def hofstaderMale(n):
if n < 0:
return;
else:
val = 0 if n == 0 else (
n - hofstaderMale(n - 1))
return val
# Driver code
print("F:", end = " ")
for i in range(0, 20):
print(hofstaderFemale(i), end = " ")
print("\n")
print("M:", end = " ")
for i in range(0, 20):
print(hofstaderMale(i), end = " ")
# This code is contributed
# by Shantanu Sharma
C#
// C# program to implement Hofstader
// Sequence using mutual recursion
using System;
class GFG {
// Female function
static int hofstaderFemale(int n)
{
if (n < 0)
return 0;
else
return (n == 0) ? 1 : n -
hofstaderFemale(n - 1);
}
// Male function
static int hofstaderMale(int n)
{
if (n < 0)
return 0;
else
return (n == 0) ? 0 : n -
hofstaderMale(n - 1);
}
// Driver Code
static public void Main ()
{
int i;
Console.WriteLine("F: ");
for (i = 0; i < 20; i++)
Console.Write(hofstaderFemale(i) + " ");
Console.WriteLine();
Console.WriteLine("M: ");
for (i = 0; i < 20; i++)
Console.Write(hofstaderMale(i) + " ");
}
}
// This code is contributed by Ajit.
PHP
<?php
// PHP program to implement
// Hofstader Sequence
// using mutual recursion
//function hofstaderFemale(int);
//int hofstaderMale(int);
// Female function
function hofstaderFemale($n)
{
if ($n < 0)
return;
else
return ($n == 0) ? 1 : $n - hofstaderFemale($n - 1);
}
// Male function
function hofstaderMale($n)
{
if ($n < 0)
return;
else
return ($n == 0) ? 0 : $n - hofstaderMale($n - 1);
}
// Driver Code
$i;
echo "F: ";
for ($i = 0; $i < 20; $i++)
echo hofstaderFemale($i), " ";
echo "\n";
echo "M: ";
for ($i = 0; $i < 20; $i++)
echo hofstaderMale($i), " ";
// This code contributed by Ajit
?>
JavaScript
<script>
// Javascript program to implement Hofstader
// Sequence using mutual recursion
// Female function
function hofstaderFemale(n)
{
if (n < 0)
return 0;
else
return (n == 0) ? 1 :
n - hofstaderFemale(n - 1);
}
// Male function
function hofstaderMale(n)
{
if (n < 0)
return 0;
else
return (n == 0) ? 0 :
n - hofstaderMale(n - 1);
}
// Driver code
let i;
document.write("F: ");
for(i = 0; i < 20; i++)
document.write(hofstaderFemale(i) + " ");
document.write("</br>");
document.write("M: ");
for(i = 0; i < 20; i++)
document.write(hofstaderMale(i) + " ");
// This code is contributed by rameshtravel07
</script>
Output:
F: 1 0 2 1 3 2 4 3 5 4 6 5 7 6 8 7 9 8 10 9
M: 0 1 1 2 2 3 3 4 4 5 5 6 6 7 7 8 8 9 9 10
Disadvantages of Circular Dependency/Mutual Recursion:
- Circular dependencies can cause a domino effect when a small local change in one module spreads into other modules and has unwanted global effects
- Circular dependencies can also result in infinite recursions or other unexpected failures.
- Circular dependencies may also cause memory leaks by preventing certain very primitive automatic garbage collectors (those that use reference counting) from deallocating unused objects.
References: Wikipedia
Explore
DSA Fundamentals
Data Structures
Algorithms
Advanced
Interview Preparation
Practice Problem