X-Git-Url: http://plrg.eecs.uci.edu/git/?p=folly.git;a=blobdiff_plain;f=folly%2FTraits.h;h=fb797f377bb72a7f860180c8ea511066c15ce0c5;hp=58d507b17e2084543aa8c3132efc707b0cfaa6ac;hb=4bec077b3dc283e75125e9cf95fad89ca6617101;hpb=db9fd491eacdbef14aba095dd9ffd1b7e51e2689 diff --git a/folly/Traits.h b/folly/Traits.h index 58d507b1..fb797f37 100644 --- a/folly/Traits.h +++ b/folly/Traits.h @@ -156,10 +156,26 @@ template using _t = typename T::type; /** + * type_t + * + * A type alias for the first template type argument. `type_t` is useful for + * controlling class-template and function-template partial specialization. + * + * Example: + * + * template + * class Container { + * public: + * template + * Container( + * type_t()...))>, + * Args&&...); + * }; + * * void_t * * A type alias for `void`. `void_t` is useful for controling class-template - * partial specialization. + * and function-template partial specialization. * * Example: * @@ -174,9 +190,9 @@ using _t = typename T::type; */ /** - * There is a bug in gcc that causes it to ignore unused template parameter - * arguments in template aliases and does not cause substitution failures. - * This defect has been recorded here: + * There is a bug in libstdc++, libc++, and MSVC's STL that causes it to + * ignore unused template parameter arguments in template aliases and does not + * cause substitution failures. This defect has been recorded here: * http://open-std.org/JTC1/SC22/WG21/docs/cwg_defects.html#1558. * * This causes the implementation of std::void_t to be buggy, as it is likely @@ -201,28 +217,19 @@ using _t = typename T::type; * The second foo() will be a redefinition because it conflicts with the first * one; void_t does not cause substitution failures - the template types are * just ignored. - * - * Till then only the non-buggy MSVC std::void_t can be used, and for the rest - * folly::void_t will continue to be used because it does not use unnamed - * template parameters for the top level implementation of void_t. */ -#if defined(_MSC_VER) - -/* using override */ using std::void_t; - -#else // defined(_MSC_VER) namespace traits_detail { -template -struct void_t_ { - using type = void; +template +struct type_t_ { + using type = T; }; } // namespace traits_detail +template +using type_t = typename traits_detail::type_t_::type; template -using void_t = _t>; - -#endif // defined(_MSC_VER) +using void_t = type_t; /** * IsRelocatable::value describes the ability of moving around @@ -301,11 +308,12 @@ struct is_trivially_copyable : std::is_trivial {}; template using is_trivially_copyable = std::is_trivially_copyable; #endif -} +} // namespace traits_detail struct Ignore { + Ignore() = default; template - /* implicit */ Ignore(const T&) {} + constexpr /* implicit */ Ignore(const T&) {} template const Ignore& operator=(T const&) const { return *this; } }; @@ -322,7 +330,7 @@ struct IsEqualityComparable decltype(std::declval() == std::declval()), bool > {}; -} +} // namespace traits_detail_IsEqualityComparable /* using override */ using traits_detail_IsEqualityComparable:: IsEqualityComparable; @@ -336,7 +344,7 @@ struct IsLessThanComparable decltype(std::declval() < std::declval()), bool > {}; -} +} // namespace traits_detail_IsLessThanComparable /* using override */ using traits_detail_IsLessThanComparable:: IsLessThanComparable; @@ -364,7 +372,7 @@ struct IsNothrowSwappable noexcept(swap(std::declval(), std::declval())) > {}; #endif -} +} // namespace traits_detail_IsNothrowSwappable /* using override */ using traits_detail_IsNothrowSwappable::IsNothrowSwappable;