2011-01-12 6 views
2

大部分がのプロジェクト名で、このクラスが導入されて以来、リンカの速度が著しく遅いプロジェクトで、次のテンプレートクラスが頻繁に使用されているとします。テンプレートクラスの特殊化/明示的なインスタンス化は、コンパイル/リンカーの速度を改善しますか?

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テンプレートを使用すると、テンプレートのインスタンス化はextern変数と同じように1回しか発生しません。

これは、コンパイラーがそれを見るたびにその引数でテンプレートをインスタンス化する必要がないため、これはコンパイル時に役立ちます。

私は自分のプロジェクトでこの機能をどのように使用するのかをまだ理解していませんが、コンパイルに役立つものはすべて私にとってプラスです。

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

1

しかし、そのような専門化を自動的に膨大な数発生させない限り、大きな問題にはなりません。また、パフォーマンスはコンパイラによって異なります。あなたはいつもそれを自分でテストすることができます(厳密なテストや多数のテスト実行がなければ、その違いが明白でないと思います)。

テンプレートが参照されているすべてのコンパイルモジュールでテンプレートが「インライン」(必ずしもインラインではありません)と宣言されている可能性があります。それが起こると、あなたはどこにでもメソッドを複製しており、リンカーはもっと多くの作業をします。比較すると、ヘッダー内の宣言だけを持つ「通常の」関数と、ただ1つの場所での定義は、コンパイルされた関数が1つだけで、リンカー(およびコンパイラ)の関数が少なくなります。リンク時コードの生成などのオプションによって、これはかなり問題になることもほとんどないこともあります。

0

あなたのツールチェーンに厳密に依存しています(この場合、少なくともリンカーとコンパイラ、多分もっと多くの場合)。

ちょうど試してみてください。ただし、ツールチェーンを1つでも変更しても結果は大きく異なる可能性があります。

1

私たちは、テンプレートが大幅にコンパイルとリンク時間を増やすことができることを見出しました。問題の1つは、テンプレートを宣言するヘッダーを含む各ファイルがそのファイルを解析し、その妥当性をチェックし、コンパイル単位によって使用されている場合、生成されたオブジェクトファイルにコードが含まれ、リンカー(複数のファイルで使用されている場合)

私たちのプロジェクトでは、ほぼすべてのファイルに含まれていたが、インスタンス化は2つしか存在しない大きなテンプレートがいくつかありました。私たちは、明示的なインスタンス化と、複数のファイルでのテンプレートコードの分離を使用することによって、コンパイル時間を大幅に改善しました。あなたを与えるだろうあなたの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 
関連する問題