Simple Divide and Conquer Example - divide-and-conquer

Here is my test divide and conquer program, but it gives me an error. I am heading in the right direction?
public class getSum {
static int sum = 0;
public static void main(String[] args) {
int[] numbers = {2,2,2,2,2,2,2,2};
int amount = 0;
amount = sumArray(0,numbers.length,numbers);
System.out.print(amount);
}
public static int sumArray(int first, int last, int[] A){
int index = last - first;
if(index == 1){
return sum;
}else if(index <= 4 && index > 1){
for(int i = first; first < last; i++){
sum += A[i];
}
return sum;
}
return (sumArray(first, last / 2, A) + sumArray(last / 2, A.length, A));
}
}
Here is the error
Exception in thread "main" java.lang.StackOverflowError
at getSum.sumArray(getSum.java:16)
I am looking for a simple example of taking an array of 16 and breaking it down to base case 4. I am having trouble completely understanding how to spit the array, then split it again. then combine all the splits in the end.

You can use recursion for divide and conquer. You keep recursing on smaller arrays until you find a match, then climb up the recusion tree.
For example: find if a number is in the array using the recursive function isIn(Number x, Array a)
Boolean isIn(Number x, Array a) {
n = a.size
if n==1 then return a[0]==x
else
return isIn(x, a[0:n/2]) or isIn(x,a[n/2:n])
}
You can see how the problem is split into two smaller problems, and so on, until it reaches the stop condition 'n==1' then it starts returning results up the call tree.
This is pseudo code, you will have to adapt the concept to the programming language you are using

Having trouble completely understanding how to spit the array, then split it again.
Using Recursion you can do that.

Related

Could you please explain me the the working of following code?

// This is a function to check if the given array is sorted or not by recurssion
#include<iostream>
using namespace std;
bool sorted(int arr[],int n)
{
if(n==1)
{
return true;
}
I am cofused here when n will reach 1 then it will return true to "restArray" after that if array is not sorted then how will "restArray" become false?
bool restArray = sorted(arr+1, n-1);
return (arr[0]<=arr[1] && restArray);
}
int main()
{
int arr[]={1,6,3,4,5};
cout<<sorted(arr,5);
return 0;
}
As in every recursion there are two cases
First the trivial case if (n == 1): An array of size 1 (ie only a single element) is always sorted. Thus it returns true and stops the recursion
And if n is still greater than 1, you do the recursive call and check if the array without the first element is sorted (bool restArray = sorted(arr+1, n-1)), then you check if the first element of the array is less than the second element (a[0] < a[1]). (btw I'd probably check for <= here) And finally you combine those two checks with &&.
So for your example, it will at some point in time check 6 < 3, which will return false thus the overall result will become false.
But for sake of optimization, I'd suggest to reorder your statements a bit, such that you won't need the recursive call, if the order of the first two elements in the array is already wrong. And as #Scheff's Cat mentioned in the comments: When you convert it to a tail recursion, any decdent compiler will be able to refactor that recursion into a (much cheaper) iteration ...
And I'd also check for n <= 1 otherwise you might end up in an infinite recursion if you method is (wrongly!) called with n = 0.
bool sorted(int arr[],int n)
{
if (n <= 1)
{
return true;
}
return arr[0] <= arr[1] && sorted(arr+1, n-1);
}
or even simpler
bool sorted(int arr[], int n) {
return n <= 1
? true
: arr[0] <= arr[1] && sorted(arr+1, n-1);
}

Recursive function that takes the sum of odd integers

The program runs but it also spews out some other stuff and I am not too sure why. The very first output is correct but from there I am not sure what happens. Here is my code:
#include <iostream>
using namespace std;
const int MAX = 10;
int sum(int arrayNum[], int n)
{
int total = 0;
if (n <= 0)
return 0;
else
for(int i = 0; i < MAX; i ++)
{
if(arrayNum[i] % 2 != 0)
total += arrayNum[i];
}
cout << "Sum of odd integers in the array: " << total << endl;
return arrayNum[0] + sum(arrayNum+1,n-1);
}
int main()
{
int x[MAX] = {13,14,8,7,45,89,22,18,6,10};
sum(x,MAX);
system("pause");
return 0;
}
The term recursion means (in the simplest variation) solving a problem by reducing it to a simpler version of the same problem until becomes trivial. In your example...
To compute the num of the odd values in an array of n elements we have these cases:
the array is empty: the result is trivially 0
the first element is even: the result will be the sum of odd elements of the rest of the array
the first element is odd: the result will be this element added to the sum of odd elements of the rest of the array
In this problem the trivial case is computing the result for an empty array and the simpler version of the problem is working on a smaller array. It is important to understand that the simpler version must be "closer" to a trivial case for recursion to work.
Once the algorithm is clear translation to code is simple:
// Returns the sums of all odd numbers in
// the sequence of n elements pointed by p
int oddSum(int *p, int n) {
if (n == 0) {
// case 1
return 0;
} else if (p[0] % 2 == 0) {
// case 2
return oddSum(p + 1, n - 1);
} else {
// case 3
return p[0] + oddSum(p + 1, n - 1);
}
}
Recursion is a powerful tool to know and you should try to understand this example until it's 100% clear how it works. Try starting rewriting it from scratch (I'm not saying you should memorize it, just try rewriting it once you read and you think you understood the solution) and then try to solve small variations of this problem.
No amount of reading can compensate for writing code.
You are passing updated n to recursive function as argument but not using it inside.
change MAX to n in this statement
for(int i = 0; i < n; i ++)
so this doesnt really answer your question but it should help.
So, your code is not really recursive. If we run through your function
int total = 0; //Start a tally, good.
if (n <= 0)
return 0; //Check that we are not violating the array, good.
else
for(int i = 0; i < MAX; i ++)
{
if(arrayNum[i] % 2 != 0) //THIS PART IS WIERD
total += arrayNum[i];
}
And the reason it is wierd is because you are solving the problem right there. That for loop will run through the list and add all the odd numbers up anyway.
What you are doing by recursing could be to do this:
What is the sum of odd numbers in:
13,14,8,7,45,89,22,18,6,10
+
14,8,7,45,89,22,18,6
+
8,7,45,89,22,18
+
7,45,89,22 ... etc
And if so then you only need to change:
for(int i = 0; i < MAX; i ++)
to
for(int i = 0; i < n; i ++)
But otherwise you really need to rethink your approach to this problem.
It's not recursion if you use a loop.
It's also generally a good idea to separate computation and output.
int sum(int arrayNum[], int n)
{
if (n <= 0) // Base case: the sum of an empty array is 0.
return 0;
// Recursive case: If the first number is odd, add it to the sum of the rest of the array.
// Otherwise just return the sum of the rest of the array.
if(arrayNum[0] % 2 != 0)
return arrayNum[0] + sum(arrayNum + 1, n - 1);
else
return sum(arrayNum + 1, n - 1);
}
int main()
{
int x[MAX] = {13,14,8,7,45,89,22,18,6,10};
cout << sum(x,MAX);
}

Understanding Recursion to generate permutations

I find recursion, apart from very straight forward ones like factorial, very difficult to understand. The following snippet prints all permutations of a string. Can anyone help me understand it. What is the way to go about to understand recursion properly.
void permute(char a[], int i, int n)
{
int j;
if (i == n)
cout << a << endl;
else
{
for (j = i; j <= n; j++)
{
swap(a[i], a[j]);
permute(a, i+1, n);
swap(a[i], a[j]);
}
}
}
int main()
{
char a[] = "ABCD";
permute(a, 0, 3);
getchar();
return 0;
}
PaulR has the right suggestion. You have to run through the code by "hand" (using whatever tools you want - debuggers, paper, logging function calls and variables at certain points) until you understand it. For an explanation of the code I'll refer you to quasiverse's excellent answer.
Perhaps this visualization of the call graph with a slightly smaller string makes it more obvious how it works:
The graph was made with graphviz.
// x.dot
// dot x.dot -Tpng -o x.png
digraph x {
rankdir=LR
size="16,10"
node [label="permute(\"ABC\", 0, 2)"] n0;
node [label="permute(\"ABC\", 1, 2)"] n1;
node [label="permute(\"ABC\", 2, 2)"] n2;
node [label="permute(\"ACB\", 2, 2)"] n3;
node [label="permute(\"BAC\", 1, 2)"] n4;
node [label="permute(\"BAC\", 2, 2)"] n5;
node [label="permute(\"BCA\", 2, 2)"] n6;
node [label="permute(\"CBA\", 1, 2)"] n7;
node [label="permute(\"CBA\", 2, 2)"] n8;
node [label="permute(\"CAB\", 2, 2)"] n9;
n0 -> n1 [label="swap(0, 0)"];
n0 -> n4 [label="swap(0, 1)"];
n0 -> n7 [label="swap(0, 2)"];
n1 -> n2 [label="swap(1, 1)"];
n1 -> n3 [label="swap(1, 2)"];
n4 -> n5 [label="swap(1, 1)"];
n4 -> n6 [label="swap(1, 2)"];
n7 -> n8 [label="swap(1, 1)"];
n7 -> n9 [label="swap(1, 2)"];
}
To use recursion effectively in design, you solve the problem by assuming you've already solved it.
The mental springboard for the current problem is "if I could calculate the permutations of n-1 characters, then I could calculate the permutations of n characters by choosing each one in turn and appending the permutations of the remaining n-1 characters, which I'm pretending I already know how to do".
Then you need a way to do what's called "bottoming out" the recursion. Since each new sub-problem is smaller than the last, perhaps you'll eventually get to a sub-sub-problem that you REALLY know how to solve.
In this case, you already know all the permutations of ONE character - it's just the character. So you know how to solve it for n=1 and for every number that's one more than a number you can solve it for, and you're done. This is very closely related to something called mathematical induction.
It chooses each character from all the possible characters left:
void permute(char a[], int i, int n)
{
int j;
if (i == n) // If we've chosen all the characters then:
cout << a << endl; // we're done, so output it
else
{
for (j = i; j <= n; j++) // Otherwise, we've chosen characters a[0] to a[j-1]
{ // so let's try all possible characters for a[j]
swap(a[i], a[j]); // Choose which one out of a[j] to a[n] you will choose
permute(a, i+1, n); // Choose the remaining letters
swap(a[i], a[j]); // Undo the previous swap so we can choose the next possibility for a[j]
}
}
}
This code and reference might help you to understand it.
// C program to print all permutations with duplicates allowed
#include <stdio.h>
#include <string.h>
/* Function to swap values at two pointers */
void swap(char *x, char *y)
{
char temp;
temp = *x;
*x = *y;
*y = temp;
}
/* Function to print permutations of string
This function takes three parameters:
1. String
2. Starting index of the string
3. Ending index of the string. */
void permute(char *a, int l, int r)
{
int i;
if (l == r)
printf("%s\n", a);
else
{
for (i = l; i <= r; i++)
{
swap((a+l), (a+i));
permute(a, l+1, r);
swap((a+l), (a+i)); //backtrack
}
}
}
/* Driver program to test above functions */
int main()
{
char str[] = "ABC";
int n = strlen(str);
permute(str, 0, n-1);
return 0;
}
Reference: Geeksforgeeks.org
Though it is little old question and already answered thought of adding my inputs to help new visitors. Also planning to explain the running time without focusing on Recursive Reconciliation.
I have written the sample in C# but easy to understand for most of the programmers.
static int noOfFunctionCalls = 0;
static int noOfCharDisplayCalls = 0;
static int noOfBaseCaseCalls = 0;
static int noOfRecursiveCaseCalls = 0;
static int noOfSwapCalls = 0;
static int noOfForLoopCalls = 0;
static string Permute(char[] elementsList, int currentIndex)
{
++noOfFunctionCalls;
if (currentIndex == elementsList.Length)
{
++noOfBaseCaseCalls;
foreach (char element in elementsList)
{
++noOfCharDisplayCalls;
strBldr.Append(" " + element);
}
strBldr.AppendLine("");
}
else
{
++noOfRecursiveCaseCalls;
for (int lpIndex = currentIndex; lpIndex < elementsList.Length; lpIndex++)
{
++noOfForLoopCalls;
if (lpIndex != currentIndex)
{
++noOfSwapCalls;
Swap(ref elementsList[currentIndex], ref elementsList[lpIndex]);
}
Permute(elementsList, (currentIndex + 1));
if (lpIndex != currentIndex)
{
Swap(ref elementsList[currentIndex], ref elementsList[lpIndex]);
}
}
}
return strBldr.ToString();
}
static void Swap(ref char Char1, ref char Char2)
{
char tempElement = Char1;
Char1 = Char2;
Char2 = tempElement;
}
public static void StringPermutationsTest()
{
strBldr = new StringBuilder();
Debug.Flush();
noOfFunctionCalls = 0;
noOfCharDisplayCalls = 0;
noOfBaseCaseCalls = 0;
noOfRecursiveCaseCalls = 0;
noOfSwapCalls = 0;
noOfForLoopCalls = 0;
//string resultString = Permute("A".ToCharArray(), 0);
//string resultString = Permute("AB".ToCharArray(), 0);
string resultString = Permute("ABC".ToCharArray(), 0);
//string resultString = Permute("ABCD".ToCharArray(), 0);
//string resultString = Permute("ABCDE".ToCharArray(), 0);
resultString += "\nNo of Function Calls : " + noOfFunctionCalls;
resultString += "\nNo of Base Case Calls : " + noOfBaseCaseCalls;
resultString += "\nNo of General Case Calls : " + noOfRecursiveCaseCalls;
resultString += "\nNo of For Loop Calls : " + noOfForLoopCalls;
resultString += "\nNo of Char Display Calls : " + noOfCharDisplayCalls;
resultString += "\nNo of Swap Calls : " + noOfSwapCalls;
Debug.WriteLine(resultString);
MessageBox.Show(resultString);
}
Steps:
For e.g. when we pass input as "ABC".
Permutations method called from Main for first time. So calling with Index 0 and that is first call.
In the else part in for loop we are repeating from 0 to 2 making 1 call each time.
Under each loop we are recursively calling with LpCnt + 1.
4.1 When index is 1 then 2 recursive calls.
4.2 When index is 2 then 1 recursive calls.
So from point 2 to 4.2 total calls are 5 for each loop and total is 15 calls + main entry call = 16.
Each time loopCnt is 3 then if condition gets executed.
From the diagram we can see loop count becoming 3 total 6 times i.e. Factorial value of 3 i.e. Input "ABC" length.
If statement's for loop repeats 'n' times to display chars from the example "ABC" i.e. 3.
Total 6 times (Factorial times) we enter into if to display the permutations.
So the total running time = n X n!.
I have given some static CallCnt variables and the table to understand each line execution in detail.
Experts, feel free to edit my answer or comment if any of my details are not clear or incorrect, I am happy correct them.
Download the sample code and other samples from here
Think about the recursion as simply a number of levels. At each level, you are running a piece of code, here you are running a for loop n-i times at each level. this window gets decreasing at each level. n-i times, n-(i+1) times, n-(i+2) times,..2,1,0 times.
With respect to string manipulation and permutation, think of the string as simply a 'set' of chars. "abcd" as {'a', 'b', 'c', 'd'}. Permutation is rearranging these 4 items in all possible ways. Or as choosing 4 items out of these 4 items in different ways. In permutations the order does matter. abcd is different from acbd. we have to generate both.
The recursive code provided by you exactly does that. In my string above "abcd", your recursive code runs 4 iterations (levels). In the first iteration you have 4 elements to choose from. second iteration, you have 3 elements to choose from, third 2 elements, and so on. so your code runs 4! calculations. This is explained below
First iteration:
choose a char from {a,b,c,d}
Second Iteration:
choose a char from subtracted set {{a,b,c,d} - {x}} where x is the char chosen from first iteration. i.e. if 'a' has been choose in first iteration, this iteration has {b,c,d} to choose from.
Third Iteration:
choose a char from subtracted set {{a,b,c,d} - {x,y}} where x and y are chosen chars from previous iterations. i.e. if 'a' is chosen at first iteration, and 'c' is chosen from 2nd, we have {b,d} to play with here.
This repeats until we choose 4 chars overall. Once we choose 4 possible char, we print the chars. Then backtrack and choose a different char from the possible set. i.e. when backtrack to Third iteration, we choose next from possible set {b,d}. This way we are generating all possible permutations of the given string.
We are doing this set manipulations so that we are not selecting the same chars twice. i.e. abcc, abbc, abbd,bbbb are invalid.
The swap statement in your code does this set construction. It splits the string into two sets free set to choose from used set that are already used. All chars on left side of i+1 is used set and right are free set. In first iteration, you are choosing among {a,b,c,d} and then passing {a}:{b,c,d} to next iteration. The next iteration chooses one of {b,c,d} and passes {a,b}:{c,d} to next iteration, and so on. When the control backtracks back to this iteration, you will then choose c and construct {a,c}, {b,d} using swapping.
That's the concept. Otherwise, the recursion is simple here running n deep and each level running a loop for n, n-1, n-2, n-3...2,1 times.

My Sieve of Eratosthenes takes too long

I have implemented Sieve of Eratosthenes to solve the SPOJ problem PRIME1. Though the output is fine, my submission exceeds the time limit. How can I reduce the run time?
int main()
{
vector<int> prime_list;
prime_list.push_back(2);
vector<int>::iterator c;
bool flag=true;
unsigned int m,n;
for(int i=3; i<=32000;i+=2)
{
flag=true;
float s = sqrt(static_cast<float>(i));
for(c=prime_list.begin();c<=prime_list.end();c++)
{
if(*c>s)
break;
if(i%(*c)==0)
{
flag=false;
break;
}
}
if(flag==true)
{
prime_list.push_back(i);
}
}
int t;
cin>>t;
for (int times = 0; times < t; times++)
{
cin>> m >> n;
if (t) cout << endl;
if (m < 2)
m=2;
unsigned int j;
vector<unsigned int> req_list;
for(j=m;j<=n;j++)
{
req_list.push_back(j);
}
vector<unsigned int>::iterator k;
flag=true;
int p=0;
for(j=m;j<=n;j++)
{
flag=true;
float s = sqrt(static_cast<float>(j));
for(c=prime_list.begin();c<=prime_list.end();c++)
{
if((*c)!=j)
{
if((*c)>s)
break;
if(j%(*c)==0)
{
flag=false;
break;
}
}
}
if(flag==false)
{
req_list.erase (req_list.begin()+p);
p--;
}
p++;
}
for(k=req_list.begin();k<req_list.end();k++)
{
cout<<*k;
cout<<endl;
}
}
}
Your code is slow because you did not implement the Sieve of Eratosthenes algorithm. The algorithm works that way:
1) Create an array with size n-1, representing the numbers 2 to n, filling it with boolean values true (true means that the number is prime; do not forget we start counting from number 2 i.e. array[0] is the number 2)
2) Initialize array[0] = false.
3) Current_number = 2;
3) Iterate through the array by increasing the index by Current_number.
4) Search for the first number (except index 0) with true value.
5) Current_number = index + 2;
6) Continue steps 3-5 until search is finished.
This algorithm takes O(nloglogn) time.
What you do actually takes alot more time (O(n^2)).
Btw in the second step (where you search for prime numbers between n and m) you do not have to check if those numbers are prime again, ideally you will have calculated them in the first phase of the algorithm.
As I see in the site you linked the main problem is that you can't actually create an array with size n-1, because the maximum number n is 10^9, causing memory problems if you do it with this naive way. This problem is yours :)
I'd throw out what you have and start over with a really simple implementation of a sieve, and only add more complexity if really needed. Here's a possible starting point:
#include <vector>
#include <iostream>
int main() {
int number = 32000;
std::vector<bool> sieve(number,false);
sieve[0] = true; // Not used for now,
sieve[1] = true; // but you'll probably need these later.
for(int i = 2; i<number; i++) {
if(!sieve[i]) {
std::cout << "\t" << i;
for (int temp = 2*i; temp<number; temp += i)
sieve[temp] = true;
}
}
return 0;
}
For the given range (up to 32000), this runs in well under a second (with output directed to a file -- to the screen it'll generally be slower). It's up to you from there though...
I am not really sure that you have implemented the sieve of Erasthotenes. Anyway a couple of things that could speed up to some extent your algorithm would be: Avoid multiple rellocations of the vector contents by preallocating space (lookup std::vector<>::reserve). The operation sqrt is expensive, and you can probably avoid it altogether by modifying the tests (stop when the x*x > y instead of checking x < sqrt(y).
Then again, you will get a much better improvement by revising the actual algorithm. From a cursory look it seems as if you are iterating over all candidates and for each one of them, trying to divide with all the known primes that could be factors. The sieve of Erasthotenes takes a single prime and discards all multiples of that prime in a single pass.
Note that the sieve does not perform any operation to test whether a number is prime, if it was not discarded before then it is a prime. Each not prime number is visited only once for each unique factor. Your algorithm on the other hand is processing every number many times (against the existing primes)
I think one way to slightly speed up your sieve is the prevention of using the mod operator in this line.
if(i%(*c)==0)
Instead of the (relatively) expensive mod operation, maybe if you iterated forward in your sieve with addition.
Honestly, I don't know if this is correct. Your code is difficult to read without comments and with single letter variable names.
The way I understand the problem is that you have to generate all primes in a range [m,n].
A way to do this without having to compute all primes from [0,n], because this is most likely what's slowing you down, is to first generate all the primes in the range [0,sqrt(n)].
Then use the result to sieve in the range [m,n]. To generate the initial list of primes, implement a basic version of the sieve of Eratosthenes (Pretty much just a naive implementation from the pseudo code in the Wikipedia article will do the trick).
This should enable you to solve the problem in very little time.
Here's a simple sample implementation of the sieve of Eratosthenes:
std::vector<unsigned> sieve( unsigned n ) {
std::vector<bool> v( limit, true ); //Will be used for testing numbers
std::vector<unsigned> p; //Will hold the prime numbers
for( unsigned i = 2; i < n; ++i ) {
if( v[i] ) { //Found a prime number
p.push_back(i); //Stuff it into our list
for( unsigned j = i + i; j < n; j += i ) {
v[i] = false; //Isn't a prime/Is composite
}
}
}
return p;
}
It returns a vector containing only the primes from 0 to n. Then you can use this to implement the method I mentioned. Now, I won't provide the implementation for you, but, you basically have to do the same thing as in the sieve of Eratosthenes, but instead of using all integers [2,n], you just use the result you found. Not sure if this is giving away too much?
Since the SPOJ problem in the original question doesn't specify that it has to be solved with the Sieve of Eratosthenes, here's an alternative solution based on this article. On my six year old laptop it runs in about 15 ms for the worst single test case (n-m=100,000).
#include <set>
#include <iostream>
using namespace std;
int gcd(int a, int b) {
while (true) {
a = a % b;
if(a == 0)
return b;
b = b % a;
if(b == 0)
return a;
}
}
/**
* Here is Rowland's formula. We define a(1) = 7, and for n >= 2 we set
*
* a(n) = a(n-1) + gcd(n,a(n-1)).
*
* Here "gcd" means the greatest common divisor. So, for example, we find
* a(2) = a(1) + gcd(2,7) = 8. The prime generator is then a(n) - a(n-1),
* the so-called first differences of the original sequence.
*/
void find_primes(int start, int end, set<int>* primes) {
int an; // a(n)
int anm1 = 7; // a(n-1)
int diff;
for (int n = start; n < end; n++) {
an = anm1 + gcd(n, anm1);
diff = an - anm1;
if (diff > 1)
primes->insert(diff);
anm1 = an;
}
}
int main() {
const int end = 100000;
const int start = 2;
set<int> primes;
find_primes(start, end, &primes);
ticks = GetTickCount() - ticks;
cout << "Found " << primes.size() << " primes:" << endl;
set<int>::iterator iter = primes.begin();
for (; iter != primes.end(); ++iter)
cout << *iter << endl;
}
Profile your code, find hotspots, eliminate them. Windows, Linux profiler links.

Why is my recursiveMinimum function not working?

#include <iostream>
using namespace std;
int recursiveMinimum(int [], int n);
int main ()
{
int theArray[3] = {1,2,3};
cout << recursiveMinimum(theArray, 0);
cout << endl;
return 0;
}
// pass in array and 0 to indicate first element
// returns smallest number in an array
int recursiveMinimum (int anArray[], int n) // nth element is smallest element in anArray
{
while (anArray[n+1] != NULL)
{
int smallest = n;
if (anArray[n+1] <= anArray[n])
smallest = n + 1;
//if last element has not been reached
return recursiveMinimum(anArray, smallest);
}
}
My function exits, but it doesn't return anything. I tried to set the base case to when the outside of the array is reached. The return 0 line in main is reached so I'm pretty sure the base case in my function is being reached.
Here is the working function:
#include <iostream>
using namespace std;
int recursiveMinimum(int a[],int min,int index,int size);
int main()
{
int a[6] = {8, 2, 55, 3, 11, 9};
cout << recursiveMinimum(a,a[0],1,6) << endl;
return 0;
}
// pass in the array, the first element,
// 1 to indicate 2nd element, and the number of elements
int recursiveMinimum(int a[],int min,int i,int size)
{
if(i == size )
return min;
else if(i < size)
{
if(a[i] < min)
recursiveMinimum(a,a[i], i + 1, size);
else
recursiveMinimum(a,min, i + 1, size);
}
}
Thank you to everyone who helped. Due to time constraints I sent out a SOS (Stack Overflow distress Signal), however next time I will definitely step through the debugger prior to asking a question.
Have you stepped through this in a debugger? It should become fairly obvious when you do.
You are recursing within the while loop:
while( condition )
recursive call
while( condition )
recursive call
.
.
.
Instead what you probably were thinking was
if( condition )
recursive call
recursive call
recursive call
you see? Get rid of the while and replace it with an "if" statement.
You need to have an end case with a recursive function.
At the moment, your function always returns itself. This will recurse until the stack runs out. You need to have a check that says "I'm done", which will return a value rather than the result of another function call.
Because your while loop never terminates. Why are you sure anArray[n+1] will ever be NULL?
You never break your recursion. Actually I wonder that this compiles as your function doesn't even have a defined return value in case it reaches the end. Also using while there seems unnecessary as the function execution stops after the return anyway.
Instead of
int recursiveMinimum(int array[], int n);
I think that recursiveMinimum should be defined as
int recursiveMinimum(int array[], int index, int length);
with the intention that recursiveMinimum will return the minimum value in array between indexes index and length (i.e., min array[i] where i in [index, length)). Of course, you want to define this recursively. So then I would note that the minimum value in array between indexes index and length is
min(array[index], recursiveMinimum(array, index + 1, length));
Of course, there are boundary cases (such as when index = length - 1). In this case you would just return array[index] as the minimum.
Hope this helps. Let me know if this does not make sense.
You're misunderstanding the point of a recursive function. If a certain condition is true, then you return the result of a call to the recursive function, otherwise you return some other value. For example, here is a recursive definition of the factorial function (e.g. 5!, or "5 factorial", is 5*4*3*2*1, which is 125):
int
factorial (int n)
{
if (n == 1)
return n;
return (n * factorial (n - 1));
}
How it works:
If n is 1, then return 1 since 1! is 1.
Otherwise, return n multiplied by one less than n.
For example, if n is 5, then the return value is the result of the expression 5 * factorial (5 - 1), which is the same as 5 * factorial (4). Of course, the same thing happens again since it's a recursive function and 4 is not 1. So you end up with 5 * factorial (4), which is the same as 5 * (4 * factorial (4 - 1)), or 5 * (4 * factorial (3)).
You should be able to see the pattern now and how the factorial function works. Your recursiveMinimum function should adhere to the same general idea -- if something is true (or not true), return the result of a call the function (possibly with some additional things like the value n inside the factorial function needs to be multiplied by the result of the factorial function), else return a certain value and code the function to handle it appropriately. In other words, you need a "final" exit condition, such as the n == 1 condition in the factorial function above.
Good luck!
int recursiveMinimum(int a[],int min,int index,int size)
{
if(index == size )
return min;
else if(i < size)
{
if(a[i] < min)
recursiveMinimum(a,a[i],++index,size);
else
recursiveMinimum(a,min,++index,size);
}
}
int main()
{
int a[] = {1,2,3,0,-4};
int min = recursiveMinimum(a,a[0],1,5));
return 0;
}
When you use recursion make sure that you must put some exit condition to end it ,otherwise you will have in infinite recursion and you program will hang.
I think finding minimum is more efficient,easy and simple using iteration rather than recursion.