We no longer inherit from boost::iterator (thus, std::iterator) on

platforms where it's not neccessary as a workaround, thus enabling the
EBO for a large class of cases

renamed iterator_facade_base -> iterator_facade_types

fixed indentation of PP directives

worked around an MSVC6 bug which shows up with STLPort debug iterators.


[SVN r1297]
This commit is contained in:
Dave Abrahams
2003-06-01 15:23:27 +00:00
parent 65fe9a13e5
commit b49d0fe184

View File

@@ -81,34 +81,55 @@ namespace boost
{}; {};
// //
// Type generator. // Generates the associated types for an iterator_facade with the
// Generates the corresponding std::iterator specialization // given parameters. Additionally generates a 'base' type for
// from the given iterator traits type // compiler/library combinations which require user-defined
// iterators to inherit from std::iterator.
// //
template <class Value, class AccessCategory, class TraversalCategory, class Reference, class Difference> template <
struct iterator_facade_base class Value
, class AccessCategory
, class TraversalCategory
, class Reference
, class Difference
>
struct iterator_facade_types
{ {
typedef iterator< typedef iterator_tag<AccessCategory, TraversalCategory> iterator_category;
iterator_tag<AccessCategory, TraversalCategory>
, typename remove_cv<Value>::type typedef typename remove_cv<Value>::type value_type;
, Difference typedef Difference difference_type;
, typename const_qualified_ptr<Value, AccessCategory>::type typedef typename const_qualified_ptr<Value, AccessCategory>::type pointer;
// The use_default support is needed for iterator_adaptor. // The use_default support is needed for iterator_adaptor.
// For practical reasons iterator_adaptor needs to specify // For practical reasons iterator_adaptor needs to specify
// a fixed number of template arguments of iterator_facade. // a fixed number of template arguments of iterator_facade.
// So use_default is its way to say: "What I really mean // So use_default is its way to say: "What I really mean
// is your default parameter". // is your default parameter".
, typename mpl::if_< typedef typename mpl::if_<
is_same<Reference, use_default> is_same<Reference, use_default>
, typename const_qualified_ref<Value, AccessCategory>::type , typename const_qualified_ref<Value, AccessCategory>::type
, Reference , Reference
>::type >::type reference;
>
type; # if defined(BOOST_NO_TEMPLATE_PARTIAL_SPECIALIZATION) \
&& (BOOST_WORKAROUND(_STLPORT_VERSION, BOOST_TESTED_AT(0x452)) \
|| BOOST_WORKAROUND(BOOST_DINKUMWARE_STDLIB, BOOST_TESTED_AT(310))) \
|| BOOST_WORKAROUND(BOOST_RWSTD_VER, BOOST_TESTED_AT(0x20101)) \
|| BOOST_WORKAROUND(BOOST_DINKUMWARE_STDLIB, <= 310)
// To interoperate with some broken library/compiler
// combinations, user-defined iterators must be derived from
// std::iterator. It is possible to implement a standard
// library for broken compilers without this limitation.
# define BOOST_ITERATOR_FACADE_NEEDS_ITERATOR_BASE 1
typedef
iterator<iterator_category, value_type, difference_type, pointer, reference>
base;
# endif
}; };
@@ -288,7 +309,7 @@ namespace boost
) )
; ;
#endif # endif
template <class Facade> template <class Facade>
static typename Facade::reference dereference(Facade const& f) static typename Facade::reference dereference(Facade const& f)
@@ -333,14 +354,11 @@ namespace boost
}; };
// //
// // iterator_facade - use as a public base class for defining new
// iterator_facade applies iterator_traits_adaptor to its traits argument. // standard-conforming iterators.
// The net effect is that iterator_facade is derived from std::iterator. This
// is important for standard library interoperability of iterator types on some
// (broken) implementations.
// //
template < template <
class Derived class Derived // The derived iterator type being constructed
, class Value , class Value
, class AccessCategory , class AccessCategory
, class TraversalCategory , class TraversalCategory
@@ -348,12 +366,17 @@ namespace boost
, class Difference = std::ptrdiff_t , class Difference = std::ptrdiff_t
> >
class iterator_facade class iterator_facade
: public detail::iterator_facade_base<Value, AccessCategory, TraversalCategory, Reference, Difference>::type # ifdef BOOST_ITERATOR_FACADE_NEEDS_ITERATOR_BASE
: public detail::iterator_facade_types<
Value, AccessCategory, TraversalCategory, Reference, Difference
>::base
# undef BOOST_ITERATOR_FACADE_NEEDS_ITERATOR_BASE
# endif
{ {
private: private:
typedef typename typedef typename
detail::iterator_facade_base<Value, AccessCategory, TraversalCategory, Reference, Difference>::type detail::iterator_facade_types<Value, AccessCategory, TraversalCategory, Reference, Difference>
super_t; types;
// //
// Curiously Recursive Template interface. // Curiously Recursive Template interface.
@@ -372,11 +395,11 @@ namespace boost
public: public:
typedef typename super_t::value_type value_type; typedef typename types::value_type value_type;
typedef typename super_t::reference reference; typedef typename types::reference reference;
typedef typename super_t::difference_type difference_type; typedef typename types::difference_type difference_type;
typedef typename super_t::pointer pointer; typedef typename types::pointer pointer;
typedef typename super_t::iterator_category iterator_category; typedef typename types::iterator_category iterator_category;
reference operator*() const reference operator*() const
{ {
@@ -452,6 +475,18 @@ namespace boost
Derived result(this->derived()); Derived result(this->derived());
return result -= x; return result -= x;
} }
# if BOOST_WORKAROUND(BOOST_MSVC, <= 1200)
// There appears to be a bug which trashes the data of classes
// derived from iterator_facade when they are assigned unless we
// define this assignment operator. This bug is only revealed
// (so far) in STLPort debug mode, but it's clearly a codegen
// problem so we apply the workaround for all MSVC6.
iterator_facade& operator=(iterator_facade const&)
{
return *this;
}
# endif
}; };
// //