当我将所有源代码放在一个文件中时,程序会成功构建。但是,当我将它们分成头文件时,我收到链接错误。
我的计划的主要内容: // C ++ _ Class_Templates.cpp
#include <iostream>
#include <vector>
#include "Queue.h"
using namespace std;
//Usage for C++ class templates
void main()
{
MyQueue<int> q;
q.Add(1);
q.Add(2);
}
Queue.h看起来像这样
#pragma once
#include <vector>
template <typename T>
class MyQueue
{
std::vector<T> data;
public:
void Add(T const &);
void Remove();
void Print();
};
并且Queue.cpp看起来像这样:
#include "Queue.h"
template <typename T> void MyQueue<T> ::Add(T const &d)
{
data.push_back(d);
}
当我尝试构建它时,我收到此错误:
1>main.obj : error LNK2019: unresolved external symbol "public: void __thiscall
MyQueue<int>::Add(int const &)" (?Add@?$MyQueue@H@@QAEXABH@Z) referenced in function _main
答案 0 :(得分:11)
简短的回答是:“你没有。”
更长的答案是:嗯,它与简短答案基本相同。有关更多信息,请参阅C ++ FAQ Lite条目"Why can't I separate the definition of my templates class from its declaration and put it inside a .cpp file?"除了某些有限使用场景(例如,当您使用一小组已知参数时,您将使用该模板,并且可以使用这些类型显式实例化它) ,当您尝试使用模板时,模板的定义必须可用。
答案 1 :(得分:1)
分离模板的声明和定义并非易事。
编译器必须看到定义能够编译特化,但它也必须知道要使用的参数。 C ++被设计为一次编译一个“编译单元”,这两个部分(定义和参数)必须同时可见。
因此,要么将所有特殊化的列表放在模板的实现文件中,要么将整个定义放在.h文件中。然而,这两种解决方案都存在缺陷。
请参阅this answer您遇到的同一问题,以获得更完整的解释。