我开始使用 C++ 概念并且在使用它们时遇到了麻烦。
例如。这里我想做一个乐观的create_unique函数。
template<typename Arg, constructible_from<Arg> CreatedClass > *1
unique_ptr<CreatedClass>
create_unique( Arg && arg ) {
return make_unique<CreatedClass>( forward<Arg>( arg ) );
}
template<typename CreatedClass, typename Arg,
enable_if_t< !is_constructible<CreatedClass, Arg>::value, int > = 0> *2
unique_ptr<CreatedClass>
create_unique( Arg && arg ) {
throw runtime_error( "CreatedClass is not constructible from arg." );
}
int main() {
auto x = create_unique2<string>("Hello"s); *3
// auto x = create_unique2<string>(42);
}
这不会编译,因为在 *1 CreatedClass 中放置在 Arg 之后。因此,为了编译它,我必须明确指定两个模板参数。 auto x = create_unique2<string, string>("Hello"s);
如果我写template<constructible_from<string> CreatedClass, typename Arg > *1
unique_ptr<CreatedClass>
create_unique( Arg && arg ) {
return make_unique<CreatedClass>( forward<Arg>( arg ) );
}
然后 *3 编译,但现在 CreatedClass 不再依赖于 Arg。在此之后,我如何指定否定案例 *2?使用老式的 enable_if 似乎有点不干净。
最佳答案
做就是了:
template <typename CreatedClass, typename Arg>
requires std::constructible_from<CreatedClass, Arg>
auto create_unique(Arg&&) -> std::unique_ptr<CreatedClass>
您不必使用更简洁的约束语法 - requires
始终可用。否定的情况将是没有约束的重载:
template <typename CreatedClass, typename Arg>
auto create_unique(Arg&&) -> std::unique_ptr<CreatedClass>
更受约束的情况将是首选。但这是非常值得怀疑的,为什么要将此错误推迟到运行时?通过没有可行的重载 create_unique
来诊断编译类型似乎更好...
关于c++ - 我如何使用 std::constructible_from,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/63325643/