Movatterモバイル変換


[0]ホーム

URL:


cppreference.com
Namespaces
Variants
    Actions

      std::void_t

      From cppreference.com
      <cpp‎ |types
       
       
      Metaprogramming library
      Type traits
      Type categories
      (C++11)
      (C++11)(DR*)
      (C++11)
      (C++11)
      (C++11)
      (C++11)
      (C++11)
      (C++11) 
      Type properties
      (C++11)
      (C++11)
      (C++14)
      (C++11)(deprecated in C++26)
      (C++11)(until C++20*)
      (C++11)(deprecated in C++20)
      (C++11)
      Type trait constants
      Metafunctions
      (C++17)
      Supported operations
      Relationships and property queries
      Type modifications
      Type transformations
      (C++11)(deprecated in C++23)
      (C++11)(deprecated in C++23)
      (C++11)
      (C++11)(until C++20*)(C++17)

      (C++11)
      void_t
      (C++17)
      Compile-time rational arithmetic
      Compile-time integer sequences
       
      Defined in header<type_traits>
      template<class...>
      using void_t=void;
      (since C++17)

      Utility metafunction that maps a sequence of any types to the typevoid. This metafunction is a convenient way to leverageSFINAE prior to C++20'sconcepts, in particular for conditionally removing functions from thecandidate set based on whether an expression is valid in theunevaluated context (such as operand todecltype expression), allowing to exist separate function overloads or specializations based on supported operations.

      [edit]Notes

      This metafunction is used in template metaprogramming to detect ill-formed types in SFINAE context:

      // primary template handles types that have no nested ::type member:template<class,class=void>struct has_type_member:std::false_type{}; // specialization recognizes types that do have a nested ::type member:template<class T>struct has_type_member<T, std::void_t<typename T::type>>:std::true_type{};

      It can also be used to detect validity of an expression:

      // primary template handles types that do not support pre-increment:template<class,class=void>struct has_pre_increment_member:std::false_type{}; // specialization recognizes types that do support pre-increment:template<class T>struct has_pre_increment_member<T,           std::void_t<decltype(++std::declval<T&>())>>:std::true_type{};

      Until the resolution ofCWG issue 1558 (a C++11 defect), unused parameters inalias templates were not guaranteed to ensure SFINAE and could be ignored, so earlier compilers require a more complex definition ofvoid_t, such as

      template<typename...Ts>struct make_void{typedefvoid type;}; template<typename...Ts>using void_t=typename make_void<Ts...>::type;
      Feature-test macroValueStdFeature
      __cpp_lib_void_t201411L(C++17)std::void_t

      [edit]Example

      Run this code
      #include <iomanip>#include <iostream>#include <map>#include <type_traits>#include <vector> // Variable template that checks if a type has begin() and end() member functionstemplate<typename,typename=void>constexprbool is_range=false; template<typename T>constexprbool is_range<T,    std::void_t<decltype(std::declval<T>().begin()),                decltype(std::declval<T>().end())>>=true; // An iterator trait those value_type is the value_type of the iterated container,// supports even back_insert_iterator (where value_type is void)template<typename T,typename=void>struct iterator_trait:std::iterator_traits<T>{}; template<typename T>struct iterator_trait<T, std::void_t<typename T::container_type>>:std::iterator_traits<typename T::container_type::iterator>{}; class A{}; #define SHOW(...) std::cout << std::setw(34) << #__VA_ARGS__ \                            << " == " << __VA_ARGS__ << '\n' int main(){std::cout<<std::boolalpha<<std::left;     SHOW(is_range<std::vector<double>>);    SHOW(is_range<std::map<int,double>>);    SHOW(is_range<double>);    SHOW(is_range<A>); using container_t=std::vector<int>;    container_t v;     static_assert(std::is_same_v<        container_t::value_type,        iterator_trait<decltype(std::begin(v))>::value_type>);     static_assert(std::is_same_v<        container_t::value_type,        iterator_trait<decltype(std::back_inserter(v))>::value_type>);}

      Output:

      is_range<std::vector<double>>   == trueis_range<std::map<int, double>> == trueis_range<double>                == falseis_range<A>                     == false

      [edit]See also

      (C++11)
      conditionallyremoves a function overload or template specialization from overload resolution
      (class template)[edit]
      Retrieved from "https://en.cppreference.com/mwiki/index.php?title=cpp/types/void_t&oldid=182522"

      [8]ページ先頭

      ©2009-2025 Movatter.jp