Seprate template class

Hi everyone, i have a big big problem with class template, i need your help

//file Array.h
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
#ifndef ARRAY_H_
#define ARRAY_H_

template <class T> class Array 
{ 
private: 
T   *m_pElement; 
int   m_iLength; 
public: 
Array(int iLength) ;
Array(const Array &obj) ;
int GetLength() ;
T & ElementAt(int iIndex) ;
T & operator [](int iIndex)  ;
Array & operator =(const Array &obj) ;
virtual ~Array(); 
};

#endif 


//File Array.cpp
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
#include<iostream>
using namespace std;
#include"Array.h"
template<class T>
Array<T>::Array(int iLength) 
{ 
	if (iLength < 0) 
	{ 
		cout << "Error!!!"; 
		return; 
	} 
	m_iLength = iLength; 
	m_pElement = new T[m_iLength]; 
} 

template<class T>
Array<T>::Array(const Array<T> &obj) 
{ 
	m_iLength = obj.m_iLength; 
	m_pElement = new T[m_iLength]; 
	   
	for (int i = 0; i < m_iLength; i++) 
	m_pElement[i] = obj.m_pElement[i]; 
} 

template<class T>
int Array<T>::GetLength() 
{ 
	return m_iLength; 
} 
template<class T>
T & Array<T>:: ElementAt(int iIndex) 
{ 
if (iIndex < 0 || iIndex >= m_iLength) 
cout << "Out of range!!!"; 
return m_pElement[iIndex]; 
} 
template<class T>
T & Array<T>::operator [](int iIndex)  
{ 
return ElementAt(iIndex); 
} 

template<class T>
Array & Array<T> ::operator =(const Array<T> &obj) 
{ 
m_iLength = obj.m_iLength; 
m_pElement = new T[m_iLength]; 
     
for (int i = 0; i < m_iLength; i++) 
m_pElement[i] = obj.m_pElement[i]; 
return *this; 
}

template<class T>
virtual Array<T>::~Array() 
{ 
	if (m_pElement != NULL) 
	delete []m_pElement; 
} 



//and main.cpp
1
2
3
4
5
6
7
8
9
10
#include "Array.h"
#include<iostream>
using namespace std;
void main() 
{ 
Array<int>   a(3); 
a[0] = 0;    a[1] = 1;    a[2] = 2; 
for (int i = 0; i < a.GetLength(); i++) 
cout << a[i] << endl; 
}


I've tried many ways:
1. put #include<Array.cpp> at the end of file Array.h
2. Change Array.cpp to Array.hpp,...

But dont work at all

I have tried to separate class template into two files for 3 days
I cant figure it out
I almost give up

Thks in advance!!!!
Last edited on
1) Post your errors.
2) Template class implementation should be in the same header file as declaration.
Here it is:

Error 2 error C2244: 'Array<T>::operator =' : unable to match function definition to an existing declaration

Error 1 error C2955: 'Array' : use of class template requires template argument list

But my exercise is separating it
Well, you cannot. At least it isn't intended by language creators.

It is simple if you understand how C++ separate compilation works. When you compiling your cpp file, compiler does not know which T you are using and what code it should generate.
You can separate them. The trick is to use an file extension that the compiler does not identify as a compiler unit (such as .tpp). Then the .tpp (or whatever you choose) can be safely included.
Thks
I ve tried but still have errors
im using Visual Studio 2010
with another exercise
i put #include"blahblah.cpp"
at the end of file .h

and in file .cpp i delete #include"blahblah.h", it worked

but with this exercies it doesnt
Array.cpp, Line 45, the return value must be Array<T>&. Also Array.h, line 15.

I agree with coder777. If you want to separate the header and the instantiation of the template code, change the name of Array.cpp to Array.tpp, and add include "Array.tpp" at line 18 of Array.h. Because of the include guards in Array.h, it won't matter whether Array.tpp includes Array.h or not.
Last edited on
> Well, you cannot.
> It is simple if you understand how C++ separate compilation works.
> When you compiling your cpp file, compiler does not know which T you are using and what code it should generate.
So if you just say which T may be used, you can separate it.
See explicit template instantiation http://www.cplusplus.com/forum/articles/14272/
<ne555>i ve tried it too

So, we cant separate it

>Compiler only compiles .cpp files, so when compiling Array.cpp, compiler doesnt know what type of T so it cant compile< That my explanation

Is it right>>???
I did it

.h
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18


template <class T> class Array 
{ 
private: 
T   *m_pElement; 
int   m_iLength; 
public: 
Array(int iLength);
Array(const Array &obj);
int GetLength() ;
T& ElementAt(int iIndex) ;
T& operator [](int iIndex)  ;
Array<T>& operator =(const Array<T> &obj) ;
virtual ~Array(); 
};



.cpp
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
#include<iostream>
using namespace std;
#include"Array.h"
template<class T>
Array<T>::Array(int iLength) 
{ 
	if (iLength < 0) 
	{ 
		cout << "Error!!"; 
		return; 
	} 
	m_iLength = iLength; 
	m_pElement = new T[m_iLength]; 
} 

template<class T>
Array<T>::Array(const Array<T> &obj) 
{ 
	m_iLength = obj.m_iLength; 
	m_pElement = new T[m_iLength]; 
	   
	for (int i = 0; i < m_iLength; i++) 
	m_pElement[i] = obj.m_pElement[i]; 
} 

template<class T>
int Array<T>::GetLength() 
{ 
	return m_iLength; 
} 
template<class T>
T & Array<T>:: ElementAt(int iIndex) 
{ 
if (iIndex < 0 || iIndex >= m_iLength) 
cout << "Out of range"; 
return m_pElement[iIndex]; 
} 
template<class T>
T & Array<T>::operator [](int iIndex)  
{ 
return ElementAt(iIndex); 
} 

template<class T>
Array<T>& Array<T> ::operator =(const Array<T> &obj) 
{ 
m_iLength = obj.m_iLength; 
m_pElement = new T[m_iLength]; 
     
for (int i = 0; i < m_iLength; i++) 
m_pElement[i] = obj.m_pElement[i]; 
return *this; 
}

template<class T>
Array<T>::~Array() 
{ 
	if (m_pElement != NULL) 
	delete []m_pElement; 
} 

template class Array<int>;
template class Array<float>;


main.cpp
1
2
3
4
5
6
7
8
9
10
#include "Array.h"
#include<iostream>
using namespace std;
void main() 
{ 
Array<int>   a(3); 
a[0] = 0;    a[1] = 1;    a[2] = 2; 
for (int i = 0; i < a.GetLength(); i++) 
cout << a[i] << endl; 
}
Topic archived. No new replies allowed.