Template class file organization

Hello:

I am new to template programming and trying to implement a simple toy template class with Visual Studio 2010.

For the sake of clarity, I would like to split the code between a header and a source file:

//b.h
#ifndef B_H
#define B_H

template <class T>
class b
{
public:
b();
~b();

};

#include "b.cpp"

#endif

//b.cpp
#include "stdafx.h"
#include "b.h"

template <class T>
b<T>::b( ) { }

template <class T>
b<T>::~b() { }

The VS2010 compiler throws two C2995 errors. The constructor and destructor seem to be already defined in the header.

1>------ Operación Generar iniciada: proyecto: Tlib, configuración: Debug Win32 ------
1>Compilando...
1>b.cpp
1>c:\users\jacques\documents\visual studio 2008\projects\tlib\tlib\b.cpp(5) : error C2995: 'b<T>::b(void)' : ya se ha definido la plantilla de función
1> c:\users\jacques\documents\visual studio 2008\projects\tlib\tlib\b.h(8) : vea la declaración de 'b<T>::b'
1>c:\users\jacques\documents\visual studio 2008\projects\tlib\tlib\b.cpp(8) : error C2995: 'b<T>::~b(void)' : ya se ha definido la plantilla de función
1> c:\users\jacques\documents\visual studio 2008\projects\tlib\tlib\b.h(9) : vea la declaración de 'b<T>::~b'

Any idea how to fix this?

Thanks in advance for your replies.
The implementation must be included in the header. (no .cpp files for templates)
Last edited on
Hi Shacktar,

Indeed implementing the template directly inside the header works.

None the less I read that it is possible to write the implementation inside the source file provided that it gets included at the end of the header.

Any hint?

Thank you.
Here are some good resources on the subject (as organizing template code can get a little tricky):

http://www.codeproject.com/KB/cpp/templatesourceorg.aspx
http://www.parashift.com/c++-faq-lite/templates.html#faq-35.12

In short, there are two solutions to organizing template code:

1. The "Inclusion Model" - keeping the template declarations and definitions together, as in putting them both in the same header file

2. The "Separation Model" - explicitly tell the compiler which template instantiations you're going to use by placing them in a separate compilation unit (this compilation unit needs to see both the template declarations and definitions). Both resources above show examples of this.

The problem with the second method is that you need to maintain another file with all your template instantiations. This could become a problem for large projects. However, the second solution may lead to less code bloat relative to the first method, so it could be the optimal solution in your case.

(Both resources mention using the "export" keyword though I haven't used it and it looks like there may be some compatibility issues with it. You may research this on your own if curious.)

If you're going to use the Inclusion Model and want to use two files for your template class, then it is bad practice to include a .cpp file. It's better to use a different file extension for the template implementation in this case (such as .tlt).

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
//b.h
#pragma once

#ifndef B_H
#define B_H

template <class T>
class b
{
public:
    b();
    ~b();
};

#include "b.tlt"

#endif 


1
2
3
4
5
6
//b.tlt
template <class T>
b<T>::b( ) { }

template <class T>
b<T>::~b() { }


You'll have to tell your editor to apply syntax highlighting to your template implementation file type.
Last edited on
Thank you Shacktar.

The code is compiling with the separation model.

May you have a nice day.
Topic archived. No new replies allowed.