c++ - OSX clang++:架构 x86_64 的未定义符号,用于 cpp 文件中显式实例化的模板
问题描述
我在 .h 文件中定义了模板类,在 .cpp 文件中定义了模板方法。此 .cpp 文件还包含通过template clas Class<type>
.
此用例在 VS2019 上与在 GCC (7.4.0) 上一样正常工作。但是,它不适用于带有 clang++ 的 OSX(Apple LLVM 版本 10.0.0 clang-1000.11.45.5)。
根据文档,我相信这是一个有效的代码。有什么办法让它在 OSX clang 下工作?
我不想将所有实现移动到 .h 因为更好的可读性并且因为我只需要两个/三个模板实例化。
这是我的测试文件:
test.h
#pragma once
template <class T>
class CTemplateTest
{
public:
int Test();
};
test.cpp
#include "test.h"
template class CTemplateTest<int>;
template class CTemplateTest<double>;
template <class T>
int CTemplateTest<T>::Test()
{
return 42;
}
main.cpp
#include "test.h"
int main(int argc, char** argv)
{
CTemplateTest<int> t1;
CTemplateTest<double> t2;
t1.Test();
t2.Test();
}
output
Undefined symbols for architecture x86_64:
"CTemplateTest<double>::Test()", referenced from:
_main in main.o
"CTemplateTest<int>::Test()", referenced from:
_main in main.o
ld: symbol(s) not found for architecture x86_64
谢谢你的帮助。
解决方案
成员函数未实例化。这并不奇怪,因为您在定义CTemplateTest<T>::Test
. 将显式实例化移到test.cpp
template <class T>
int CTemplateTest<T>::Test()
{
return 42;
}
template class CTemplateTest<int>;
template class CTemplateTest<double>;
我建议你在标题中添加一个显式的实例化声明
template <class T>
class CTemplateTest
{
public:
int Test();
};
extern template class CTemplateTest<int>;
extern template class CTemplateTest<double>;
这指示编译器在使用特定特化时放弃大部分隐式实例化。它会知道完整的定义在别处。
此外,它还具有良好的文档目的。现在只需阅读标题即可知道支持的类型。
推荐阅读
- assembly - MASM32:显示一天内的时间
- file - 我们如何将文件上传到 chrome 扩展程序?
- networking - torrent 用户如何从其他用户那里获取大量数据?
- java - Java - 如何将一个整数分成 5 个随机部分
- vba - 从 Excel-VBA 中的范围获取工作簿名称和工作表名称
- swift - 从字符串 [Swift, Spritekit] 中获取自定义类的类型
- php - php - 从字符串的最后一个字符中删除第 n 个字符
- django - 使用保存的表单而不是清理的表单 django
- apache-zookeeper - ZooKeeper 如何提供顺序一致性
- javascript - webpack 错误无法解析 './src'