Подтвердить что ты не робот

С++ шаблон и файлы заголовков

поэтому я слышал, что шаблоны С++ не следует разделять на .h и .cpp...

например, такой шаблон:

template <class T>
class J{

   T something;

}

Это правда? почему это так?

если из-за этого мне нужно будет вставить оба объявления и реализацию в один и тот же файл, следует ли помещать его в файл .h или файл .cpp?

4b9b3361

Ответ 1

Headers.

Это потому, что шаблоны создаются во время компиляции, а не времени ссылки, а разные единицы перевода (примерно эквивалентные вашим файлам .cpp) только "знают друг о друге" во время ссылки. Заголовки, как правило, широко известны во время компиляции, потому что вы #include их в любой единицы перевода, которая им нужна.

Подробнее читайте https://isocpp.org/wiki/faq/templates.

Ответ 2

Причина, по которой вы не можете поместить шаблон с шаблоном в файл .cpp, заключается в том, что для "компиляции".cpp файла вам нужно знать, какой тип используется вместо T. Поскольку он стоит templated class (например, ваш класс J) не имеет достаточной информации для компиляции. Таким образом, все должно быть в заголовках.

Если вы хотите разбить реализацию на другой файл для чистоты, лучше всего использовать файл .hxx. Например: внутри вашего файла заголовка, J.h, put:

#ifndef _J_H__
#define _J_H__

template <class T> class J{  // member definitions };

#include "j.hxx"

#endif // _J_H__

а затем в j.hxx у вас будет

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.

Наконец, в вашем .cpp файле, который использует шаблонный класс, позвоните ему K.cpp, у вас будет:

#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.
}

Ответ 3

Да, это правда. Декларация и реализация обычно помещаются в файл заголовка вместе. Некоторые компиляторы экспериментировали с ключевым словом export, что позволило бы их разделить, но это было удалено из С++ 0x. Проверьте эту запись в FAQ для всех грязных деталей.

Ответ 4

Если вам нужен код шаблона для использования другими единицами перевода (файлы .cpp), вам нужно поместить реализацию в файл .h, иначе эти другие единицы не смогут создать экземпляр шаблона (развернуть его в зависимости от типов, которые они используют).

Если ваша функция шаблона создается только в одном .cpp файле, вы можете определить ее там. Иногда это происходит, когда класс имеет частную функцию-член, которая является шаблоном (и она вызывается только из файла реализации, а не файла заголовка класса).