diff --git a/libstdc++-v3/ChangeLog b/libstdc++-v3/ChangeLog index 97f94fdf80d9..c38d7499d47d 100644 --- a/libstdc++-v3/ChangeLog +++ b/libstdc++-v3/ChangeLog @@ -1,3 +1,14 @@ +2010-10-05 Paolo Carlini + + * include/std/type_traits (_GLIBCXX_HAS_NESTED_TYPE): Add. + * include/std/functional (_Has_result_type_helper, + _Has_result_type): Remove; use the above to define __has_result_type. + * include/bits/stl_iterator_base_types.h: Use the above to define + __has_iterator_category. + * include/bits/allocator.h (__has_allocator_type): Use the above. + * include/bits/cpp_type_traits.h (__has_iterator_category, + __is_iterator): Remove. + 2010-10-05 Sebastian Huber Jonathan Wakely diff --git a/libstdc++-v3/include/bits/allocator.h b/libstdc++-v3/include/bits/allocator.h index 2d7a4e129ace..e73ab7ea5cd3 100644 --- a/libstdc++-v3/include/bits/allocator.h +++ b/libstdc++-v3/include/bits/allocator.h @@ -48,7 +48,7 @@ #include #ifdef __GXX_EXPERIMENTAL_CXX0X__ -#include +#include // For _GLIBCXX_HAS_NESTED_TYPE #endif _GLIBCXX_BEGIN_NAMESPACE(std) @@ -210,26 +210,10 @@ _GLIBCXX_BEGIN_NAMESPACE(std) static const allocator_arg_t allocator_arg = allocator_arg_t(); - template - class __has_allocator_type - : public __sfinae_types - { - template - struct _Wrap_type - { }; - - template - static __one __test(_Wrap_type*); - - template - static __two __test(...); - - public: - static const bool __value = sizeof(__test<_Tp>(0)) == 1; - }; +_GLIBCXX_HAS_NESTED_TYPE(allocator_type) template::__value> + bool = __has_allocator_type<_Tp>::value> struct __uses_allocator_helper : public false_type { }; diff --git a/libstdc++-v3/include/bits/cpp_type_traits.h b/libstdc++-v3/include/bits/cpp_type_traits.h index 030494665a08..0d7b9ff09fcd 100644 --- a/libstdc++-v3/include/bits/cpp_type_traits.h +++ b/libstdc++-v3/include/bits/cpp_type_traits.h @@ -414,34 +414,6 @@ _GLIBCXX_BEGIN_NAMESPACE(std) }; #endif - template - class __has_iterator_category - { - typedef char __one; - typedef struct { char __arr[2]; } __two; - - template - struct _Wrap_type - { }; - - template - static __one __test(_Wrap_type*); - - template - static __two __test(...); - - public: - static const bool __value = sizeof(__test<_Tp>(0)) == 1; - }; - - template - struct __is_iterator - { - enum { __value = (__has_iterator_category<_Tp>::__value - || __is_pointer<_Tp>::__value) }; - typedef typename __truth_type<__value>::__type __type; - }; - _GLIBCXX_END_NAMESPACE #endif //_CPP_TYPE_TRAITS_H diff --git a/libstdc++-v3/include/bits/stl_iterator_base_types.h b/libstdc++-v3/include/bits/stl_iterator_base_types.h index 20fee58a0a83..7b1eafd12839 100644 --- a/libstdc++-v3/include/bits/stl_iterator_base_types.h +++ b/libstdc++-v3/include/bits/stl_iterator_base_types.h @@ -65,7 +65,7 @@ #include #ifdef __GXX_EXPERIMENTAL_CXX0X__ -# include // For __has_iterator_category +# include // For _GLIBCXX_HAS_NESTED_TYPE #endif _GLIBCXX_BEGIN_NAMESPACE(std) @@ -137,8 +137,11 @@ _GLIBCXX_BEGIN_NAMESPACE(std) * provide tighter, more correct semantics. */ #ifdef __GXX_EXPERIMENTAL_CXX0X__ + +_GLIBCXX_HAS_NESTED_TYPE(iterator_category) + template::__value> + bool = __has_iterator_category<_Iterator>::value> struct __iterator_traits { }; template diff --git a/libstdc++-v3/include/std/functional b/libstdc++-v3/include/std/functional index dcd7ab83d2e8..f781d9e0477a 100644 --- a/libstdc++-v3/include/std/functional +++ b/libstdc++-v3/include/std/functional @@ -63,33 +63,7 @@ namespace std template class _Mem_fn; - /** - * Actual implementation of _Has_result_type, which uses SFINAE to - * determine if the type _Tp has a publicly-accessible member type - * result_type. - */ - template - class _Has_result_type_helper : __sfinae_types - { - template - struct _Wrap_type - { }; - - template - static __one __test(_Wrap_type*); - - template - static __two __test(...); - - public: - static const bool value = sizeof(__test<_Tp>(0)) == 1; - }; - - template - struct _Has_result_type - : integral_constant::type>::value> - { }; +_GLIBCXX_HAS_NESTED_TYPE(result_type) /// If we have found a result_type, extract it. template @@ -108,7 +82,7 @@ namespace std */ template struct _Weak_result_type_impl - : _Maybe_get_result_type<_Has_result_type<_Functor>::value, _Functor> + : _Maybe_get_result_type<__has_result_type<_Functor>::value, _Functor> { }; /// Retrieve the result type for a function type. diff --git a/libstdc++-v3/include/std/type_traits b/libstdc++-v3/include/std/type_traits index f4d0b267759c..cde741eb43a3 100644 --- a/libstdc++-v3/include/std/type_traits +++ b/libstdc++-v3/include/std/type_traits @@ -696,6 +696,35 @@ namespace std type; }; + /** + * Use SFINAE to determine if the type _Tp has a publicly-accessible + * member type _NTYPE. + */ +#define _GLIBCXX_HAS_NESTED_TYPE(_NTYPE) \ + template \ + class __has_##_NTYPE##_helper \ + : __sfinae_types \ + { \ + template \ + struct _Wrap_type \ + { }; \ + \ + template \ + static __one __test(_Wrap_type*); \ + \ + template \ + static __two __test(...); \ + \ + public: \ + static const bool value = sizeof(__test<_Tp>(0)) == 1; \ + }; \ + \ + template \ + struct __has_##_NTYPE \ + : integral_constant::type>::value> \ + { }; + // @} group metaprogramming }