Namespaces
Variants

std::experimental:: conjunction

From cppreference.net
Definido en el encabezado <experimental/type_traits>
template < class ... B >
struct conjunction ;
(library fundamentals TS v2)

Forma la conjunción lógica de los rasgos de tipo B... , efectuando una operación AND lógica sobre la secuencia de rasgos.

La especialización std :: experimental :: conjunction < B1, ..., BN > tiene una base pública e inequívoca que es

  • si sizeof... ( B ) == 0 , std:: true_type ; de lo contrario
  • el primer tipo Bi en B1, ..., BN para el cual bool ( Bi :: value ) == false , o BN si no existe tal tipo.

Los nombres de los miembros de la clase base, excepto conjunction y operator= , no están ocultos y están disponibles de manera inequívoca en conjunction .

La conjunción es de cortocircuito: si hay un argumento de tipo plantilla Bi con bool ( Bi :: value ) == false , entonces instanciar conjunction < B1, ..., BN > :: value no requiere la instanciación de Bj :: value para j > i .

Contenidos

Parámetros de plantilla

B... - cada argumento de plantilla Bi para el cual Bi :: value es instanciado debe ser utilizable como clase base y definir el miembro value que sea convertible a bool

Plantilla de variable auxiliar

template < class ... B >
constexpr bool conjunction_v = conjunction < B... > :: value ;
(biblioteca fundamentals TS v2)

Implementación posible

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_t<bool(B1::value), conjunction<Bn...>, B1> {};

Notas

Una especialización de conjunction no necesariamente hereda de std:: true_type o de std:: false_type : simplemente hereda del primer B cuyo ::value, convertido a bool, es false, o del último B cuando todos se convierten a true. Por ejemplo, conjunction < std:: integral_constant < int , 2 > , std:: integral_constant < int , 4 >> :: value es 4 .

Ejemplo

#include <experimental/type_traits>
#include <iostream>
// func is enabled if all Ts... have the same type
template<typename T, typename... Ts>
constexpr std::enable_if_t<std::experimental::conjunction_v<std::is_same<T, Ts>...>>
func(T, Ts...)
{
    std::cout << "All types are the same.\n";
}
template<typename T, typename... Ts>
constexpr std::enable_if_t<!std::experimental::conjunction_v<std::is_same<T, Ts>...>>
func(T, Ts...)
{
    std::cout << "Types differ.\n";
}
int main()
{
    func(1, 2'7, 3'1);    
    func(1, 2.7, '3');    
}

Salida:

All types are the same.
Types differ.

Véase también

metafunción AND lógica variádica
(plantilla de clase)