这些是我的文件:
--------[ c.hpp ]--------
#ifndef _C
#define _C
#include<iostream>
class C
{
public:
template<class CARTYPE> void call(CARTYPE& c);
};
#endif
--------[c.cpp]--------
#include "c.hpp"
template<class CARTYPE> void C::call(CARTYPE& c)
{
//make use of c somewhere here
std::cout<<"Car"<<std::endl;
}
--------[ v.cpp ]--------
class Merc
{};
--------[ main.cpp ]--------
#include "c.hpp"
#include "v.cpp"
//#include "c.cpp"
int main()
{
Merc m;
C someCar;
someCar.call(m);
}//main
我可以使用命令 g++ -c main.cpp 和 g++ -c c.cpp 等为上述所有文件生成“.o”文件。
但是当我尝试将“.o”文件与 g++ -o car c.o main.o v.o 链接时
我收到此错误:
main.o: In function `main':
main.cpp:(.text+0x17): undefined reference to `void C::call<Merc>(Merc&)'
collect2: ld returned 1 exit status
当我取消注释 main.cpp 中的 #include "c.cpp" 行时,错误消失了,但我觉得以这种方式包含 cpp 文件可能是不好的做法。我这样做错了吗?在创建单独的对象文件并链接它们时,是否有更好的方法来满足模板化声明的需要?
p.s:我在更复杂的类结构中使用模板化函数。这里显示的只是一个小例子,目的是向您展示我所面临的错误类型。
我相信这是因为当你编译时c.cpp
编译器不知道它需要生成代码C::call<Merc>(Merc&)
,当你编译时main.cpp
它没有定义C::call<T>(T&)
从中实例化C::call<Merc>(Merc&)
.
模板定义本质上是语义宏,非常类似于预处理器的宏#define
词法宏它们必须在使用它们的编译单元中可见。
本文内容由网友自发贡献,版权归原作者所有,本站不承担相应法律责任。如您发现有涉嫌抄袭侵权的内容,请联系:hwhale#tublm.com(使用前将#替换为@)