如果每个参数都可转换为特定类型,则启用构造函数

Enable a ctor if each argument is convertible to a specific type

只要有多个参数并且每个参数都可转换为类型 value_type,我想启用 class foo 的构造函数。我尝试了以下方法:

struct foo
{
    using value_type = /* some type */;

    template<class... Ts,
        std::enable_if_t<(sizeof...(Ts) > 0) && std::conjunction_v<std::is_convertible_v<Ts, value_type>...>, int> = 0>
    explicit foo(Ts&&... vs)
    {
    }
};

假设foo::value_type = float。我试图声明 foo bar{ 1 }; 并观察到 ​​ctor 被禁用。为了查看发生了什么,我从模板中删除了 std::conjunction_v 部分并添加了

static_assert(std::conjunction_v<std::is_convertible_v<Ts, value_type>...>, "");

到body。现在我的编译器 (MSVC 14.1 / Clang) 产生错误

template argument for template type parameter must be a type

static_assert(std::conjunction_v<std::is_convertible_v<Ts, value_type>...>, "");               
                             // ^

这里到底是什么问题?c

正如所述,模板类型参数的模板参数必须是类型。在 std::conjunction<T...> 中,T 应该是类型,但 std::is_convertible_v<X, Y> 直接产生值。

试试这个:

std::conjunction_v<std::is_convertible<Ts, value_type>...>
//                                    ^ no `_v`.

顺便说一句,因为你的目标是 C++17,你可以使用 fold expression 而不是 std::conjunction:

template<class... Ts,
  std::enable_if_t<((sizeof...(Ts) > 0) && ... && std::is_convertible_v<Ts, value_type>), int> _ = 0
>