请考虑以下代码:
#include <iostream>
#include <cinttypes>
template<class T>
void f();
template<>
inline void f<long long>() {
std::cout<<"f<long long>()"<<std::endl;
}
int main(int , char** ) {
std::cout<<"sizeof(long)="<<sizeof(long)<<std::endl;
std::cout<<"sizeof(long long)="<<sizeof(long long)<<std::endl;
f<int64_t>();
return 0;
}
32 位 G++ 4.6.3 成功编译并生成输出:
sizeof(long)=4
sizeof(long long)=8
f<long long>()
但是,在 64 位 G++ 4.6.3 下编译会产生链接器错误:
undefined reference to `void f<long>()'
ld returned 1 exit status
即使编译和运行 f<int64_t>()
行注释掉了产生:
sizeof(long)=8
sizeof(long long)=8
64 位 G++ 将f<long>
和f<long long>
视为不同的函数,即使long
和long long
的大小相同,这是否有充分的理由,或者这是我应该报告的错误?
int64_t
的基础类型可以是满足要求的任何内容。可以在一个平台上long
,在另一个平台上long long
。
由于您为long long
提供了专用化,并且通用版本没有正文,因此如果int64_t
不是long long
则会获得未定义的引用。
是的,f<long>
和f<long long>
是不同的功能是有充分理由的:这是因为标准说long
和long long
是不同的类型。它们在某些平台上碰巧宽度相同的事实并不重要,特别是因为它们在另一个平台上的宽度可能不同。
它们是不同的类型,因此必须区别对待。类型的大小不会影响重载或模板选择。
您的问题可能是int64_t
在一个系统上long
,而在另一个系统上long long
。当将 typedefs 与重载或模板相结合时,这是一个问题。