我有一个类来评估集合代数,但希望对它进行模板化。
在某一刻看起来有点像这样
set.h:
template<typename T>
class SetEvaluation
{
public:
SetEvaluation<T>();
std::set<T>
evaluate(std::string in_expression);
}
set.cpp
template<typename T>
std::set<T>
SetEvaluation<T>::evaluate(std::string expression)
{
std::set<T> result;
etc etc...
}
但是我在编译时遇到了未定义的引用错误。
是否可以将返回类型声明为std :: set&lt; T&gt;然后将std :: string作为类模板参数传递。
类中没有错误,但只有当我尝试实例化SetEvaluation&lt; std :: string&gt;
有人可以解释这个问题吗?
感谢
答案 0 :(得分:2)
模板类和函数有点特殊,需要在头文件中定义。然后,只要您想要使用该模板类,该头文件就必须是#included。如果您尝试在cpp文件中定义模板函数链接器并尝试从另一个cpp文件调用该函数,则链接器将无法解析该引用,因为编译器不知道该用于参数T的内容当它使用模板定义编译文件时。解决此问题的最佳方法是1)在头文件中定义函数,2)#include它在任何需要的地方。有关此问题的更多信息,请参见C++ faq。
使用Comeau C ++编译器还有另一种解决方法,因为它支持'export'关键字,但是在C ++ 0X中不推荐使用该关键字。
答案 1 :(得分:1)
template<typename T>
class SetEvaluation
in .h
并定义构造函数 至少是一个空的或评论出来
public:
SetEvaluation<T>() {}
好的,在那种情况下,使用想要从其他文件中使用它。在这种情况下,你必须 使用.cc文件中的此语法显式实例化此模板:
template std::set<std::string> SetEvaluation<std::string>::evaluate(std::string expression);
或者您必须将定义放在头文件
中答案 2 :(得分:0)
对于通用解决方案,将模板方法定义为头文件中的内联,在类主体中或之后: [对于给定的编译器系统,您可能会这样做。]
template<typename T>
class SetEvaluation
{
public:
SetEvaluation<T>() { etc. etc.}
std::set<T>
evaluate(const std::string& in_expression);
};
template<typename T>
inline std::set<T>
SetEvaluation<T>::evaluate(const std::string& expression)
{
std::set<T> result;
// etc etc...
}