Reputation:
Note : Code is posted below.
I want class dynamic array
to be able to instantiate the merge_inner
class. So I added a public function like this:
merge_sort() // merge_sort() is function in class dynamic_array
{
merge_inner<T> M1;
}
However this is in one file and merge_inner is defined below dynamic_array. How do I create a class prototype so that dynamic array know that merge_inner is a real class.
The error given is.
merge_inner not declared in scope
Thanks
#include "c_include.cpp"
using namespace std;
template <class T> class dynamic_array
{
protected:
T* array;
public:
int size;
void rorder();
void order();
void randorder();
void print_operator(ostream&)const;
dynamic_array(int sizein)
{
size=sizein;
array=new T[size]();
}
merge_sort()
{
merge_inner<T> M1;
}
};
template <class T> void dynamic_array<T>::print_operator(ostream &os=cout)const
{
for (int i = 0; i < size; i++) os << array[i] << endl;
}
template <class T> void dynamic_array<T>::randorder()
{
srand(time(NULL));
int *ap;
for(ap=array;ap!=array+size;++ap){*ap=rand();}
}
template <class T> void dynamic_array<T>::order()
{
int *ap,i=0;
for(ap=array;ap!=array+size;++ap)
{
*ap=i;
++i;
}
}
template <class T> void dynamic_array<T>::rorder()
{
int *ap,i=size-1;
for(ap=array;ap!=array+size;++ap)
{
*ap=i;
--i;
}
}
template<class T> ostream& operator<<(ostream& stream, dynamic_array<T> const& data)
{
data.print_operator(stream);
return stream;
}
/*
Merge Sort
*/
template <class T> class merge_inner : public dynamic_array <T>
{
using dynamic_array<T>::array;
private:
const static int size;
int scratch[];
void flip_if_unordered(int &x, int &y)
{
if(array[x]>array[y])
{
int tmp=array[x];
array[x]=array[y];
array[y]=tmp;
}
}
void merge_algo(int &left, int &right_begin, int &right)
{
int iter,iter_left=left,iter_right=right_begin;
for(iter=left;iter<=right;++iter)
{
if( (iter_right>right) || ((iter_left < right_begin) && (array[iter_left]<=array[iter_right])))
{
scratch[iter]=array[iter_left];
++iter_left;
}
else
{
scratch[iter]=array[iter_right];
++iter_right;
}
}
for(iter=left;iter<=right;++iter){array[iter]=scratch[iter];}
}
void merge_recurse(int left,int right)
{
int left_end=(left+((right-left)/2));
int right_begin=left_end+1;
if(((left+1)==right)){flip_if_unordered(left,right);return;}
else if ((left==right)){return;}
else
{
merge_recurse(left,left_end);
merge_recurse(right_begin,right);
merge_algo(left,right_begin,right);
}
}
public:
merge_inner()
{
scratch = new T[size]();
if(scratch != NULL){merge_recurse(0, size);}
}
};
/*Quick Sort
void quick_sort()
{
quick_recurse(0,size);
}
void quick_recurse(int left, int right)
{
int l = left, r = right, tmp;
int pivot = array[(left + right) / 2];
while (l <= r)
{
while (array[l] < pivot)l++;
while (array[r] > pivot)r--;
if (l <= r)
{
tmp = array[l];
array[l] = array[r];
array[r] = tmp;
l++;
r--;
}
}
if (left < r)quick_recurse(left, r);
if (l < right)quick_recurse(l, right);
}
*/
Upvotes: 0
Views: 640
Reputation: 477040
You have to add a forward declaration of merge_inner
template before you define dynamic array
:
template <typename> class merge_inner;
Note that this suffices and you can declare merge_inner<T> M1;
even though the template hasn't been defined yet. This is because dynamic_array
is itself a template, and the complete type merge_inner<T>
is only required when the outer template is itself instantiated.
Upvotes: 1
Reputation: 11114
Just separate your declaration and your implementation.
In your dynamic_array
, have this code:
// Declare, but don't implement yet
dynamic_array(int sizein);
merge_sort();
Then further down in your file, after you have declared merge_inner
, put the implementation of the previously-declared functions:
dynamic_array::dynamic_array(int sizein)
{
size=sizein;
array=new T[size]();
}
dynamic_array::merge_sort()
{
merge_inner<T> M1;
}
They could even be in a separate file that gets #included at the end of your file. That way, your interface is easy to read, and your implementation is separated out.
Upvotes: 2