在另一个标头

时间:2015-08-25 16:56:09

标签: c++ templates linker

我有一个模板化的&#34;集合&#34;类。我不希望在每个源文件中重新编译代码。但是此集合应该与未定义模板类的DataTypes(class SpecialDataMember : DataMember)一起使用。 这就是为什么我无法在模板源文件中强制实例化(通过将定义移动到源文件并添加template LinkCollection<DataMember>;),因为模板的定义必须可以在其他源文件中访问(& #34; SpecialDataMember.cpp&#34;。)

是否可以制作&#34; SpecialDataMember.o&#34;保留LinkCollection<SpecialDataMember>的代码。 SpecialDataMember.h的每个包含者都应该知道我将LinkCollection<SpecialDataMember>留给链接器。

我看到两个选项,但我不知道它们是否有效:

  1. 制作两个模板标题(带有标题保护),其中一个没有定义。
  2. SpecialDataMember.h

    // ..
    include "LinkCollection.h"
    // ..
    

    SpecialDataMember.cpp

    // .. 
    include "LinkCollectionImpl.h"
    // .. 
    include "SpecialDataMember.h"
    // .. 
    template LinkCollection<SpecialDataMember>;
    

    &#34; SpecialDataMember.h&#34;的所有包含者将不知道模板的定义,因此他们将让链接器完成他的工作。链接器将在LinkCollection<SpecialDataMember>中找到SpecialDataMember.o的实例化。那是对的吗? 但我必须维护两个头文件。有没有更好的方法来获得这种效果?

    1. 使用模板派生类
    2. 如果我在&#34; class SpecialDataMemberLinkCollection : LinkCollection<SpecialDataMemberLink>&#34;中创建一个特殊的SpecialDataMember头文件和源文件,我可以引用这个特殊的类,因此编译器知道该类的实例化和基类模板,并将工作留给链接器。这会按预期工作吗?

1 个答案:

答案 0 :(得分:3)

  

是否可以使“SpecialDataMember.o”保留LinkCollection<SpecialDataMember>的代码。 SpecialDataMember.h的每个包含者都应该知道我将LinkCollection<SpecialDataMember>留给链接器。

简单,只需加上:

extern template class LinkCollection<SpecialDataMember>;
标题中的

,告诉编译器不要实例化该模板并将其留给另一个文件。

然后在一个SpecialDataMember.cpp文件中提供该实例化:

template class LinkCollection<SpecialDataMember>;