【发布时间】:2016-03-16 10:29:13
【问题描述】:
以下 C++11 代码可使用 g++ 4.7.4、g++ 4.8.5、g++ 4.9.3 和 g++ 5.3.0 编译,但不能使用 clang++ 3.7.1 或 clang++ 3.8.0(主干 254750):
template <typename F, F f> struct MetaValue {};
template <typename T> class IntSpec;
template <int V> class IntSpec<MetaValue<int, V> > {};
// note: template is declared here:
template <typename T> class PtrSpec;
template <void * V> class PtrSpec<MetaValue<void *, V> > {};
int main() {
IntSpec<MetaValue<int, 0> >();
// implicit instantiation of undefined template 'PtrSpec<MetaValue<void *, nullptr> >'
PtrSpec<MetaValue<void *, nullptr> >();
}
Clang 仅在 PtrSpec<> 的实例化时出错,但在 IntSpec<> 上没有。这是编译器错误、标准中的歧义还是我在编写代码时总是需要考虑的问题?如果可能,请提供参考。
编辑:我的进一步分析发现以下两种编译器都适用:
template <typename F, F f> struct MetaValue {};
// note: template is declared here:
template<typename T> class PtrSpec;
template <int * V> class PtrSpec<MetaValue<int *, V> > {};
extern int x;
int main() { PtrSpec<MetaValue<int *, &x> >(); }
但如果我将&x 更改为nullptr,我会使用clang++ 得到implicit instantiation of undefined template 'PtrSpec<MetaValue<int *, nullptr> >'。
【问题讨论】:
-
使用 Clang 提交错误。他们会想要解决这个问题。
-
@Graznarak Nah,没有足够的动力。
标签: c++ c++11 g++ clang++ compiler-bug