|
||||
Section 35:
|
[35.13] How can I avoid linker errors with my template functions? Updated!
[Recently updated due to C++11 syntax. Click here to go to the next FAQ in the "chain" of recent changes]
Tell your C++ compiler which instantiations to make while it is compiling your template function's .cpp file. As an example, consider the header file foo.h which contains the following template function declaration: // File "foo.h" template<typename T> extern void foo();Now suppose file foo.cpp actually defines that template function: // File "foo.cpp" #include <iostream> #include "foo.h" template<typename T> void foo() { std::cout << "Here I am!\n"; }Suppose file main.cpp uses this template function by calling foo<int>(): // File "main.cpp" #include "foo.h" int main() { foo<int>(); ... }If you compile and (try to) link these two .cpp files, most compilers will generate linker errors. There are two solutions for this. The first solution is to physically move the definition of the template function into the .h file, even if it is not an inline function. This solution may (or may not!) cause significant code bloat, meaning your executable size may increase dramatically (or, if your compiler is smart enough, may not; try it and see). The other solution is to leave the definition of the template function in the .cpp file and simply add the line template void foo<int>(); to that file: // File "foo.cpp" #include <iostream> #include "foo.h" template<typename T> void foo() { std::cout << "Here I am!\n"; } template void foo<int>();If you can't modify foo.cpp, simply create a new .cpp file such as foo-impl.cpp as follows: // File "foo-impl.cpp" #include "foo.cpp" template void foo<int>();Notice that foo-impl.cpp #includes a .cpp file, not a .h file. If that's confusing, click your heels twice, think of Kansas, and repeat after me, "I will do it anyway even though it's confusing." You can trust me on this one. But if you don't trust me or are simply curious, the rationale is given earlier. |