构造函数SFINAE和继承在clang中失败
Constructor SFINAE and inheritence fails in clang
以下代码在GCC下编译良好,但在clang中失败并出现错误:
没有用于初始化"条形"的匹配构造函数
问题似乎是clang认为Foo的模板构造函数被Bar的模板构造函数隐藏或覆盖。
这是clang中的bug还是GCC中的非标准化特性?
如何解决此问题?我不能更改Foo,因为它是第三方。
#include <type_traits>
struct Foo {
Foo() = default;
template<typename T, std::enable_if_t<std::is_trivially_copyable_v<T>>* = nullptr>
Foo(T& object) {}
};
struct Bar : public Foo {
using Foo::Foo;
template<typename T, std::enable_if_t<!std::is_trivially_copyable_v<T>>* = nullptr>
Bar(T& object) {}
};
int main() {
int i;
Bar s{i};
}
https://gcc.godbolt.org/z/etvpvF
Clang是正确的。[命名空间.udcl]/14:
(emhpasis矿(
当using声明符将声明从基类带入中的派生类、成员函数和成员函数模板派生类重写和/或隐藏成员函数和成员具有相同名称的函数模板、参数类型列表、,基类中的cv限定符和ref限定符(如果有的话(而不是冲突(。此类隐藏或重写的声明被排除在外来自using声明符引入的声明集。
这意味着,在这种情况下,foo
的继承构造函数模板被Bar
的构造函数模板隐藏,无法进行查找。请注意,隐藏时只考虑名称、参数类型列表、cv限定符和ref限定符,即使对于模板也是如此。
struct Foo {
Foo() = default;
template<typename T>
Foo(T& object, std::enable_if_t<std::is_trivially_copyable_v<T>>* = nullptr) {}
};
struct Bar : public Foo {
using Foo::Foo;
template<typename T>
Bar(T& object, std::enable_if_t<!std::is_trivially_copyable_v<T>>* = nullptr) {}
};
实例
在这个版本中,构造函数模板被继承得很好,并在重载解析中使用,正如人们所期望的那样。
将您自己的SFINAE检查移动到c'tor的参数中,而不更改Foo
似乎也可以解决它:
struct Foo {
Foo() = default;
template<typename T, std::enable_if_t<std::is_trivially_copyable_v<T>>* = nullptr>
Foo(T& object) {}
};
struct Bar : public Foo {
using Foo::Foo;
template<typename T>
Bar(T& object, std::enable_if_t<!std::is_trivially_copyable_v<T>>* = nullptr) {}
};
实例
Clang认为原始模板的签名与基类中的签名相同。因此,它认为基类版本是隐藏的。
相关文章:
- 结构化绑定初始值设定项表单 { 赋值表达式 } 对于 clang 上的数组类型失败
- clang:错误:链接器命令失败,退出代码为 1(使用 -v 查看调用) - 体系结构的未定义符号 x86_64:
- 如何修复 clang: 错误:链接器命令失败,退出代码为 1(使用 -v 查看调用)
- 编译花絮 g++, clang++, 使用 libboost -- g++8 编译失败时 g++7 成功;
- 编译成功,使用 clang 5.0.1/6.0.0 ,在 5.0.2/6.0.1 时失败
- "Make"失败并出现 Clang 错误 - 如何从 Clang 获得错误?
- Android NDK.Build命令失败.未定义的引用.clang++:错误:链接器命令失败,退出代码为1
- 带有引用的std::tuple在clang中编译失败,但在gcc中编译失败
- 构造函数SFINAE和继承在clang中失败
- 继承的构造函数,在 clang++3.9 中编译,在 g++ 7 中失败
- C++ XCODE ld:找不到体系结构x86_64 clang 的符号:错误:链接器命令失败,退出代码为 1(使用 -
- clang:错误:链接器命令失败,C++代码中的退出代码为 1(使用 -v 查看调用)
- C++指向成员的指针的类内初始化会使 MSVC 失败(但 GCC/Clang 工作)
- 在 GCC 中工作的外行构造函数模板在 Clang 中失败
- enable_if is_same constexpr函数使MSVC失败(但在Clang,GCC中效果很好)
- C++编译错误:ld:找不到体系结构x86_64 clang 的符号:错误:链接器命令失败,退出代码为 1(使用 -v
- ld:找不到体系结构x86_64 clang 的符号:错误:链接器命令失败,退出代码为 1(使用 -v 查看调用)
- 线性重载:为什么 clang 在 GCC 编译时失败?
- 为什么 clang ++ 编译代码而 clang -x C++ 失败?ncurses with std::string.
- 为什么这个static_assert只在OSX上以clang失败,而在其他地方却没有