I have the following code
void mergesort(int size, int ar[], int temp[])
{
if(size <=1)
{
return;}
else
{
int i = 0;
int mid = size/2;
int *left = &ar[0];
int *right = &ar[mid];
int *rend = &ar[size];
int *lend = right;
mergesort(mid,left,temp);
mergesort(size-mid,right,temp);
for(i=0; i<size;i++)
{
if(left < lend && (*left < *right || right >= rend))
{
temp[i] = *left++;
}
else
{
temp[i] = *right++;
}
}
for(i = 0; i < size; i++)
{
ar[i] = temp[i];
}
}
}
I couldn't understand how this if statement works:
if(left < lend && (*left < *right || right >= rend))
{
temp[i] = *left++;
}
else
{
temp[i] = *right++;
}
Can you tell me what's going on in there? Why do we have to compare addresses? (left < lend and right >= rend)
Here's how the mergesort function is called from main
const int SIZE = 8;
int array[SIZE] = {3,6,1,-9,0,2,4,5};
int temp[SIZE];
mergesort(SIZE, array,temp);
In order to choose the input between the left or right sequences, you need to know if the sequence is exhausted. You check this by testing the pointer to see if it's beyond the valid range. left < lend
returns true
if the left sequence is not exhausted, and right >= rend
returns true
if the right sequence is exhausted. Thus the if
will be taken when the left sequence isn't exhausted, and either the left item is less than the right item or the right sequence is exhausted.
If you were following the standard library iterator conventions, you would never check for <
or >
in a comparison. left != lend
and right == rend
would work just as well in the code you posted.
P.S. two thoughts that aren't part of your question:
int
s it doesn't matter since you can't tell one identical int
from another, but if this was just a key in part of a larger structure it could matter greatly. It's just a matter of replacing <
with <=
.Taking all the above suggestions together you end up with:
if (left != lend && (right == rend || *left <= *right))