diff options
Diffstat (limited to 'boost/bimap/container_adaptor/container_adaptor.hpp')
-rw-r--r-- | boost/bimap/container_adaptor/container_adaptor.hpp | 291 |
1 files changed, 291 insertions, 0 deletions
diff --git a/boost/bimap/container_adaptor/container_adaptor.hpp b/boost/bimap/container_adaptor/container_adaptor.hpp new file mode 100644 index 0000000000..8e78090a9b --- /dev/null +++ b/boost/bimap/container_adaptor/container_adaptor.hpp @@ -0,0 +1,291 @@ +// Boost.Bimap +// +// Copyright (c) 2006-2007 Matias Capeletto +// +// Distributed under the Boost Software License, Version 1.0. +// (See accompanying file LICENSE_1_0.txt or copy at +// http://www.boost.org/LICENSE_1_0.txt) + +/// \file container_adaptor/container_adaptor.hpp +/// \brief Container adaptor to build a type that is compliant to the concept of a container. + +#ifndef BOOST_BIMAP_CONTAINER_ADAPTOR_CONTAINER_ADAPTOR_HPP +#define BOOST_BIMAP_CONTAINER_ADAPTOR_CONTAINER_ADAPTOR_HPP + +#if defined(_MSC_VER) && (_MSC_VER>=1200) +#pragma once +#endif + +#include <boost/config.hpp> + +#include <utility> + +#include <boost/mpl/if.hpp> +#include <boost/mpl/aux_/na.hpp> +#include <boost/bimap/container_adaptor/detail/identity_converters.hpp> +#include <boost/iterator/iterator_traits.hpp> + +#include <boost/bimap/container_adaptor/detail/functor_bag.hpp> +#include <boost/mpl/vector.hpp> +#include <boost/mpl/copy.hpp> +#include <boost/mpl/front_inserter.hpp> +#include <boost/call_traits.hpp> + + + +namespace boost { +namespace bimaps { + +/// \brief Container Adaptor toolbox, easy way to build new containers from existing ones. + +namespace container_adaptor { + +/// \brief Container adaptor to build a type that is compliant to the concept of a container. + +template +< + class Base, + + class Iterator, + class ConstIterator, + + class IteratorToBaseConverter = ::boost::mpl::na, + class IteratorFromBaseConverter = ::boost::mpl::na, + class ValueToBaseConverter = ::boost::mpl::na, + class ValueFromBaseConverter = ::boost::mpl::na, + + class FunctorsFromDerivedClasses = mpl::vector<> +> +class container_adaptor +{ + // MetaData ------------------------------------------------------------- + + public: + + typedef Iterator iterator; + typedef ConstIterator const_iterator; + + typedef BOOST_DEDUCED_TYPENAME iterator_value < iterator >::type value_type; + typedef BOOST_DEDUCED_TYPENAME iterator_pointer < iterator >::type pointer; + typedef BOOST_DEDUCED_TYPENAME iterator_reference< iterator >::type reference; + typedef BOOST_DEDUCED_TYPENAME iterator_reference< const_iterator >::type const_reference; + + typedef BOOST_DEDUCED_TYPENAME Base::size_type size_type; + typedef BOOST_DEDUCED_TYPENAME Base::difference_type difference_type; + + typedef BOOST_DEDUCED_TYPENAME mpl::if_< ::boost::mpl::is_na<IteratorToBaseConverter>, + // { + ::boost::bimaps::container_adaptor::detail:: + iterator_to_base_identity + < + BOOST_DEDUCED_TYPENAME Base::iterator , iterator, + BOOST_DEDUCED_TYPENAME Base::const_iterator , const_iterator + >, + // } + // else + // { + IteratorToBaseConverter + // } + + >::type iterator_to_base; + + typedef BOOST_DEDUCED_TYPENAME mpl::if_< ::boost::mpl::is_na<IteratorFromBaseConverter>, + // { + ::boost::bimaps::container_adaptor::detail:: + iterator_from_base_identity + < + BOOST_DEDUCED_TYPENAME Base::iterator , iterator, + BOOST_DEDUCED_TYPENAME Base::const_iterator , const_iterator + >, + // } + // else + // { + IteratorFromBaseConverter + // } + + >::type iterator_from_base; + + typedef BOOST_DEDUCED_TYPENAME mpl::if_< ::boost::mpl::is_na<ValueToBaseConverter>, + // { + ::boost::bimaps::container_adaptor::detail:: + value_to_base_identity + < + BOOST_DEDUCED_TYPENAME Base::value_type, + value_type + >, + // } + // else + // { + ValueToBaseConverter + // } + + >::type value_to_base; + + typedef BOOST_DEDUCED_TYPENAME mpl::if_< ::boost::mpl::is_na<ValueFromBaseConverter>, + // { + ::boost::bimaps::container_adaptor::detail:: + value_from_base_identity + < + BOOST_DEDUCED_TYPENAME Base::value_type, + value_type + >, + // } + // else + // { + ValueFromBaseConverter + // } + + >::type value_from_base; + + // ACCESS ----------------------------------------------------------------- + + public: + + explicit container_adaptor(Base & c) : dwfb(c) {} + + protected: + + typedef Base base_type; + + typedef container_adaptor container_adaptor_; + + const Base & base() const { return dwfb.data; } + Base & base() { return dwfb.data; } + + // Interface -------------------------------------------------------------- + + public: + + size_type size() const { return base().size(); } + size_type max_size() const { return base().max_size(); } + bool empty() const { return base().empty(); } + + iterator begin() + { + return this->template functor<iterator_from_base>()( base().begin() ); + } + + iterator end() + { + return this->template functor<iterator_from_base>()( base().end() ); + } + + const_iterator begin() const + { + return this->template functor<iterator_from_base>()( base().begin() ); + } + + const_iterator end() const + { + return this->template functor<iterator_from_base>()( base().end() ); + } + + + iterator erase(iterator pos) + { + return this->template functor<iterator_from_base>()( + base().erase(this->template functor<iterator_to_base>()(pos)) + ); + } + + iterator erase(iterator first, iterator last) + { + return this->template functor<iterator_from_base>()( + base().erase( + this->template functor<iterator_to_base>()(first), + this->template functor<iterator_to_base>()(last) + ) + ); + } + + void clear() + { + base().clear(); + } + + template< class InputIterator > + void insert(InputIterator iterBegin, InputIterator iterEnd) + { + for( ; iterBegin != iterEnd ; ++iterBegin ) + { + base().insert( this->template + functor<value_to_base>()( *iterBegin ) + ); + } + } + + std::pair<iterator, bool> insert( + BOOST_DEDUCED_TYPENAME ::boost::call_traits< value_type >::param_type x) + { + std::pair< BOOST_DEDUCED_TYPENAME Base::iterator, bool > r( + base().insert( this->template functor<value_to_base>()(x) ) + ); + + return std::pair<iterator, bool>( this->template + functor<iterator_from_base>()(r.first),r.second + ); + } + + iterator insert(iterator pos, + BOOST_DEDUCED_TYPENAME ::boost::call_traits< value_type >::param_type x) + { + return this->template functor<iterator_from_base>()( + base().insert( + this->template functor<iterator_to_base>()(pos), + this->template functor<value_to_base>()(x)) + ); + } + + void swap( container_adaptor & c ) + { + base().swap( c.base() ); + } + + // Access to functors ---------------------------------------------------- + + protected: + + template< class Functor > + Functor & functor() + { + return dwfb.template functor<Functor>(); + } + + template< class Functor > + Functor const & functor() const + { + return dwfb.template functor<Functor>(); + } + + // Data ------------------------------------------------------------------ + + private: + + ::boost::bimaps::container_adaptor::detail::data_with_functor_bag + < + Base &, + + BOOST_DEDUCED_TYPENAME mpl::copy + < + mpl::vector + < + iterator_to_base, + iterator_from_base, + value_to_base, + value_from_base + >, + + mpl::front_inserter< FunctorsFromDerivedClasses > + + >::type + + > dwfb; +}; + + +} // namespace container_adaptor +} // namespace bimaps +} // namespace boost + + +#endif // BOOST_BIMAP_CONTAINER_ADAPTOR_CONTAINER_ADAPTOR_HPP |