使用外部模板 (C++11)
TemplHeader.h
TemplHeader.h
template<typename T>
void f();
TemplCpp.cpp
TemplCpp.cpp
template<typename T>
void f(){
//...
}
//explicit instantation
template void f<T>();
Main.cpp
#include "TemplHeader.h"
extern template void f<T>(); //is this correct?
int main() {
f<char>();
return 0;
}
这是使用 extern 模板
的正确方法,还是我只将这个关键字用于类模板,如图 2 所示?
Is this the correct way to use extern template
, or do I use this keyword only for class templates as in Figure 2?
TemplHeader.h
TemplHeader.h
template<typename T>
class foo {
T f();
};
TemplCpp.cpp
TemplCpp.cpp
template<typename T>
void foo<T>::f() {
//...
}
//explicit instantation
template class foo<int>;
Main.cpp
#include "TemplHeader.h"
extern template class foo<int>();
int main() {
foo<int> test;
return 0;
}
我知道将所有这些放在一个头文件中是好的,但是如果我们在多个文件中实例化具有相同参数的模板,那么我们会得到多个相同的定义,编译器会将它们全部删除(一个除外)以避免错误.我如何使用 extern 模板
?可以只用在类上,还是也可以用在函数上?
I know it is good to put all of this in one header file, but if we instantiate templates with the same parameters in multiple files, then we got multiple same definitions and the compiler will remove them all (except one) to avoid errors. How do I use extern template
? Can we use it only for classes, or can we use it for functions too?
此外,图 1 和图 2 可以扩展为模板位于单个头文件中的解决方案.在这种情况下,我们需要使用 extern template
关键字来避免多个相同的实例化.这是否也仅适用于类或函数?
Also, Figure 1 and Figure 2 may be expanded to a solution where templates are in a single header file . In that case, we need to use the extern template
keyword to avoid multiple same instantations. Is this only for classes or functions too?
推荐答案
你应该只使用 extern template
强制编译器在 时不实例化模板您知道 它将在其他地方实例化.它用于减少编译时间和目标文件大小.
You should only use extern template
to force the compiler to not instantiate a template when you know that it will be instantiated somewhere else. It is used to reduce compile time and object file size.
例如:
// header.h
template<typename T>
void ReallyBigFunction()
{
// Body
}
// source1.cpp
#include "header.h"
void something1()
{
ReallyBigFunction<int>();
}
// source2.cpp
#include "header.h"
void something2()
{
ReallyBigFunction<int>();
}
这将产生以下目标文件:
This will result in the following object files:
source1.o
void something1()
void ReallyBigFunction<int>() // Compiled first time
source2.o
void something2()
void ReallyBigFunction<int>() // Compiled second time
如果两个文件链接在一起,一个voidReallyBigFunction
将被丢弃,导致浪费编译时间和目标文件大小.
If both files are linked together, one void ReallyBigFunction<int>()
will be discarded, resulting in wasted compile time and object file size.
为了不浪费编译时间和目标文件大小,有一个 extern
关键字使编译器不编译模板函数.您应该使用这个当且仅当您知道它在其他地方的同一个二进制文件中使用.
To not waste compile time and object file size, there is an extern
keyword which makes the compiler not compile a template function. You should use this if and only if you know it is used in the same binary somewhere else.
将 source2.cpp
更改为:
// source2.cpp
#include "header.h"
extern template void ReallyBigFunction<int>();
void something2()
{
ReallyBigFunction<int>();
}
将产生以下目标文件:
source1.o
void something1()
void ReallyBigFunction<int>() // compiled just one time
source2.o
void something2()
// No ReallyBigFunction<int> here because of the extern
当这两个链接在一起时,第二个目标文件将只使用第一个目标文件中的符号.无需丢弃,不会浪费编译时间和目标文件大小.
When both of these will be linked together, the second object file will just use the symbol from the first object file. No need for discard and no wasted compile time and object file size.
这应该只在一个项目中使用,就像当你多次使用像 vector
这样的模板时,你应该使用 extern
除了一个源文件.
This should only be used within a project, like in times when you use a template like vector<int>
multiple times, you should use extern
in all but one source file.
这也适用于类和函数合二为一,甚至模板成员函数.
This also applies to classes and function as one, and even template member functions.
相关文章