C++11 中的合取类型特征
conjunction type traits in C++11
我需要检查 std::enable_if
中的可变参数:
使用 C++17 我会写:
template <typename A, typename ...B>
class Foo : public A, public B...
{
public:
template <typename = std::enable_if_t<std::is_default_constructible_v<A> &&
(std::is_default_constructible_v<B> && ...)>>
Foo()
{}
Foo(A &&a, B && ... b)
: A(std::forward<A>(a)),
B(std::forward<B>(b))...
{}
};
但是C++11没有这样扩展参数包的特性。它也不提供 std::conjunction
.
用C++11实现联合的简单方法是什么?
我想带递归的 SFINAE 就足够了,但我无法控制它。
您需要一个可以对可变参数进行合取运算的工具。
#include <iostream>
#include <type_traits>
template<class...> struct conjunction : std::true_type { };
template<class B1> struct conjunction<B1> : B1 { };
template<class B1, class... Bn>
struct conjunction<B1, Bn...>
: std::conditional<bool(B1::value), conjunction<Bn...>, B1>::type {};
template <typename A, typename ...B>
class Foo : public A, public B...
{
public:
template <typename std::enable_if<std::is_default_constructible<A>::value &&
conjunction<std::is_default_constructible<B>...>::value, bool>::type = true>
Foo()
{}
Foo(A &&a, B && ... b)
: A(std::forward<A>(a)),
B(std::forward<B>(b))...
{}
};
struct A {};
struct B {};
struct C {
C(int x) {}
};
int main()
{
Foo<A, B> foo;
//Foo<A, B, C> bar;
return 0;
}
基于 C++17 中可用的 https://en.cppreference.com/w/cpp/types/conjunction。
试图从不同的角度看问题...
鉴于此,如果我没记错的话,std::tuple
是默认可构造的当且仅当(当且仅当)元组的每种类型都是默认可构造的,那
呢
template <typename
= typename std::enable_if<std::is_default_constructible<std::tuple<A, B...>::value>::type>
Foo()
{ }
或
template <typename = decltype(std::tuple<A, B...>())>
Foo()
{ }
?
我需要检查 std::enable_if
中的可变参数:
使用 C++17 我会写:
template <typename A, typename ...B>
class Foo : public A, public B...
{
public:
template <typename = std::enable_if_t<std::is_default_constructible_v<A> &&
(std::is_default_constructible_v<B> && ...)>>
Foo()
{}
Foo(A &&a, B && ... b)
: A(std::forward<A>(a)),
B(std::forward<B>(b))...
{}
};
但是C++11没有这样扩展参数包的特性。它也不提供 std::conjunction
.
用C++11实现联合的简单方法是什么? 我想带递归的 SFINAE 就足够了,但我无法控制它。
您需要一个可以对可变参数进行合取运算的工具。
#include <iostream>
#include <type_traits>
template<class...> struct conjunction : std::true_type { };
template<class B1> struct conjunction<B1> : B1 { };
template<class B1, class... Bn>
struct conjunction<B1, Bn...>
: std::conditional<bool(B1::value), conjunction<Bn...>, B1>::type {};
template <typename A, typename ...B>
class Foo : public A, public B...
{
public:
template <typename std::enable_if<std::is_default_constructible<A>::value &&
conjunction<std::is_default_constructible<B>...>::value, bool>::type = true>
Foo()
{}
Foo(A &&a, B && ... b)
: A(std::forward<A>(a)),
B(std::forward<B>(b))...
{}
};
struct A {};
struct B {};
struct C {
C(int x) {}
};
int main()
{
Foo<A, B> foo;
//Foo<A, B, C> bar;
return 0;
}
基于 C++17 中可用的 https://en.cppreference.com/w/cpp/types/conjunction。
试图从不同的角度看问题...
鉴于此,如果我没记错的话,std::tuple
是默认可构造的当且仅当(当且仅当)元组的每种类型都是默认可构造的,那
template <typename
= typename std::enable_if<std::is_default_constructible<std::tuple<A, B...>::value>::type>
Foo()
{ }
或
template <typename = decltype(std::tuple<A, B...>())>
Foo()
{ }
?