2011-01-12 3 views
2

Предположим, что следующий класс шаблонов сильно используется в проекте с главным образом int, так как скорость ввода и скорость компоновщика заметно ниже с момента введения этого класса.Содержит ли специализация шаблона или явное инстанцирование скорость компиляции/компоновщика?

template <typename T> 
class MyClass 
{ 
void Print() 
{ 
    std::cout << m_tValue << std::endl;; 
} 
T m_tValue; 
} 

Будет ли определять скорость сбора данных специализации? например.

template <> 
class MyClass<int> 
{ 
void Print() 
{ 
    std::cout << m_tValue << std::endl;; 
} 
int m_tValue; 
} 

Или явное создание экземпляров предлагает лучшее решение? например.

template class MyClass<int>; 
+0

@sbi, Вы правильно, спасибо, я отредактировал мой ответ, не могли бы вы повторно оценить его правильность? – Stormenet

+0

Хорошо, я должен был сказать, что я отредактировал мой * вопрос *, а не мой ответ;) – Stormenet

ответ

2

в C++ 0x вы сможете использовать шаблоны extern, чтобы экземпляры шаблонов выполнялись только один раз, как и внешние переменные.

Это должно помочь во время компиляции, поскольку компилятору не нужно было бы создавать шаблон с его аргументами каждый раз, когда он его видит.

Я еще не понял, каким образом я буду использовать эту функцию в своих проектах, но все, что может помочь скомпилировать время, - плюс для меня.

http://www2.research.att.com/~bs/C++0xFAQ.html#extern-templates

1

Делая программу более сложным - больше, и требует больше устранения неоднозначности в колл-сайте - в общем, компилятор будет медленнее не быстрее.

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

Возможно, скорость компоновщика снижена, поскольку шаблон объявляется «встроенным» (хотя и не обязательно встроенным) во все модули компиляции, в которых он ссылается. Когда это происходит, вы дублируете метод по всему месту, и компоновщик получает больше работы. Для сравнения, «нормальная» функция с просто объявлением в заголовке и определением только в одном месте приведет только к одной скомпилированной функции и, следовательно, к меньшему числу функций для компоновщика (и компилятора). В зависимости от таких параметров, как генерация кода link-time, это может иметь значение совсем немного или почти совсем.

0

Он строго зависит от вашей инструментальной цепочки (в данном случае не менее компоновщик и компилятор, возможно, больше).

Просто попробуйте, но имейте в виду, что результаты могут сильно различаться, изменяя даже одну часть вашей инструментальной цепочки.

1

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

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

Для вашего Exemple, что даст вам:

// MyClass.h 
template < typename T > 
class MyClass 
{ 
void Print(); 
T m_tValue; 
} 

// MyClass.inl 
#ifdef MY_CLASS_METHODS_ARE_NOT_INLINE 
# define MY_CLASS_INLINE 
#else 
# define MY_CLASS_INLINE inline 
#endif 

template < typename T > 
MY_CLASS_INLINE void MyClass<T>::Print() 
{ 
    std::cout << m_tValue << std::endl; 
} 

#undef MY_CLASS_INLINE 

// MyClass.cpp 
#include "MyClass.h" 

#define MY_CLASS_METHODS_ARE_NOT_INLINE 
#include "MyClass.inl" 

template class MyClass<int>; 
template void MyClass<int>::Print(); 

#undef MY_CLASS_METHODS_ARE_NOT_INLINE