
It must be useful. It could be more useful if it supports 'is_std_pair' and 'is_std_vector' etc. Also, <std_pair_fwd.hpp> and <std_vector_fwd.hpp> etc could be useful.
My first attempt was implemented this way, by simply forward declaring std containers: namespace std { template<class T, class Alloc> class vector; } template<class T, class Alloc> struct is_container< std::vector<T, Alloc> > : public boost::true_type { typedef sequence_tag container_category; }; This of course didn't scale very well, since it required is_container<> to be manually specialized for every container class. I needed something that worked automatically, so I decided for the following implementation.. Do you think it would be better to forward declare classes instead? (i.e., multi_index, ptr_container, array etc..) #ifndef TT_CONTAINER_TRAITS_HPP_INCLUDED #define TT_CONTAINER_TRAITS_HPP_INCLUDED #include <boost/type_traits/config.hpp> #include <boost/mpl/has_xxx.hpp> #include <boost/mpl/if.hpp> #include <boost/type_traits/detail/bool_trait_def.hpp> namespace container_traits { struct non_container_tag {}; struct container_tag {}; struct sequence_container_tag : public container_tag {}; struct associative_container_tag : public container_tag {}; struct hashed_container_tag : public associative_container_tag {}; template<class T, class Tag = container_tag> struct is_container; namespace detail { BOOST_MPL_HAS_XXX_TRAIT_DEF(value_type); BOOST_MPL_HAS_XXX_TRAIT_DEF(iterator); BOOST_MPL_HAS_XXX_TRAIT_DEF(size_type); BOOST_MPL_HAS_XXX_TRAIT_DEF(reference); BOOST_MPL_HAS_XXX_TRAIT_DEF(key_type); BOOST_MPL_HAS_XXX_TRAIT_DEF(hasher); BOOST_TT_AUX_BOOL_TRAIT_DEF1( has_container_traits, T, has_value_type<T>::value & has_iterator<T>::value & has_size_type<T>::value & has_reference<T>::value) } BOOST_TT_AUX_BOOL_TRAIT_PARTIAL_SPEC2_1( class T, is_container, T, container_tag, detail::has_container_traits<T>::value) BOOST_TT_AUX_BOOL_TRAIT_PARTIAL_SPEC2_1( class T, is_container, T, sequence_container_tag, detail::has_container_traits<T>::value &!detail::has_key_type<T>::value) BOOST_TT_AUX_BOOL_TRAIT_PARTIAL_SPEC2_1( class T, is_container, T, associative_container_tag, detail::has_container_traits<T>::value &detail::has_key_type<T>::value) BOOST_TT_AUX_BOOL_TRAIT_PARTIAL_SPEC2_1( class T, is_container, T, hashed_container_tag, detail::has_container_traits<T>::value &detail::has_key_type<T>::value &detail::has_hasher<T>::value) #include <boost/type_traits/detail/bool_trait_undef.hpp> template<class T> struct container_category_of { typedef typename boost::mpl::if_ < detail::has_container_traits<T>, typename boost::mpl::if_ < detail::has_key_type<T>, typename boost::mpl::if_ < detail::has_hasher<T>, hashed_container_tag, associative_container_tag >::type, sequence_container_tag >::type, non_container_tag >::type type; }; } #endif On 14/05/07, shunsuke <pstade.mb@gmail.com > wrote:
Christian Holmquist wrote:
Hello,
I've had much use of a small traits class for identifying types that matches the STL Container concept (roughly) . Two functions is made available, is_container<T> and container_category_of<T>.
is_container simply evaluates to true_type or false_type, container_category_of tries to categorize T with the following tags.
struct non_container_tag {}; struct container_tag {}; struct sequence_container_tag : public container_tag {}; struct associative_container_tag : public container_tag {}; struct hashed_container_tag : public associative_container_tag {};
template<class T, class Tag = container_tag> struct is_container
It must be useful. It could be more useful if it supports 'is_std_pair' and 'is_std_vector' etc. Also, <std_pair_fwd.hpp> and <std_vector_fwd.hpp> etc could be useful.
-- Shunsuke Sogame
_______________________________________________ Unsubscribe & other changes: http://lists.boost.org/mailman/listinfo.cgi/boost