La razón por la que no puede poner una clase con plantilla en un archivo .cpp es porque para "compilar" un archivo .cpp debe saber cuál es el tipo que se está utilizando en lugar de T. Tal como está una clase con plantilla (como su clase J) no tiene suficiente información para compilar. Por lo tanto, debe ser todo en encabezados.
Si desea dividir la implementación en otro archivo para la limpieza, la mejor práctica es utilizar un archivo .hxx. De esta manera: dentro de su archivo de cabecera, JH, poner:
#ifndef _J_H__
#define _J_H__
template <class T> class J{ // member definitions };
#include "j.hxx"
#endif // _J_H__
y luego, en j.hxx usted tendrá
template <class T> J<T>::J() { // constructor implementation }
template <class T> J<T>::~J() { // destructor implementation }
template <class T> void J<T>::memberFunc() { // memberFunc implementation }
// etc.
último en su archivo .cpp que utiliza la clase de plantilla, vamos llamarlo K.cpp tendrá:
#include "J.h" // note that this always automatically includes J.hxx
void f(void)
{
J<double> jinstance; // now the compiler knows what the exact type is.
}
existe una respuesta en el C++ FAQ: http://www.parashift.com/c++-faq-lite/templates.html#faq-35.12 – birryree