Merge pull request #9 from boostorg/develop

Merge develop into master

Tested with gcc-4.2.1 on Darwin.
This commit is contained in:
Noel Belcourt
2014-09-06 11:18:28 -06:00
101 changed files with 1253 additions and 1100 deletions

0
doc/BidirectionalTraversal.rst Executable file → Normal file
View File

0
doc/ForwardTraversal.rst Executable file → Normal file
View File

0
doc/GNUmakefile Executable file → Normal file
View File

0
doc/IncrementableIterator.rst Executable file → Normal file
View File

0
doc/LvalueIterator.rst Executable file → Normal file
View File

0
doc/ReadableIterator.rst Executable file → Normal file
View File

0
doc/SinglePassIterator.rst Executable file → Normal file
View File

0
doc/SwappableIterator.rst Executable file → Normal file
View File

0
doc/WritableIterator.rst Executable file → Normal file
View File

0
doc/counting_iterator.pdf Executable file → Normal file
View File

0
doc/docutils.sty Executable file → Normal file
View File

0
doc/facade-and-adaptor.pdf Executable file → Normal file
View File

0
doc/facade_iterator_category.rst Executable file → Normal file
View File

0
doc/filter_iterator.pdf Executable file → Normal file
View File

0
doc/function_output_iterator.pdf Executable file → Normal file
View File

0
doc/indirect_iterator.pdf Executable file → Normal file
View File

0
doc/indirect_reference_ref.rst Executable file → Normal file
View File

0
doc/interoperability-revisited.rst Executable file → Normal file
View File

0
doc/iterator_adaptor.pdf Executable file → Normal file
View File

0
doc/iterator_adaptor_tutorial.rst Executable file → Normal file
View File

0
doc/iterator_archetypes.html Executable file → Normal file
View File

0
doc/iterator_archetypes.pdf Executable file → Normal file
View File

0
doc/iterator_archetypes.rst Executable file → Normal file
View File

0
doc/iterator_concepts.pdf Executable file → Normal file
View File

0
doc/iterator_concepts.rst Executable file → Normal file
View File

0
doc/iterator_facade.pdf Executable file → Normal file
View File

0
doc/iterator_facade_tutorial.rst Executable file → Normal file
View File

31
doc/iterator_traits.html Executable file → Normal file
View File

@ -3,11 +3,11 @@
<html xmlns="http://www.w3.org/1999/xhtml" xml:lang="en" lang="en"> <html xmlns="http://www.w3.org/1999/xhtml" xml:lang="en" lang="en">
<head> <head>
<meta http-equiv="Content-Type" content="text/html; charset=utf-8" /> <meta http-equiv="Content-Type" content="text/html; charset=utf-8" />
<meta name="generator" content="Docutils 0.5: http://docutils.sourceforge.net/" /> <meta name="generator" content="Docutils 0.11: http://docutils.sourceforge.net/" />
<title>Iterator Traits</title> <title>Iterator Traits</title>
<meta name="author" content="David Abrahams" /> <meta name="author" content="David Abrahams" />
<meta name="organization" content="Boost Consulting" /> <meta name="organization" content="Boost Consulting" />
<meta name="date" content="2006-09-11" /> <meta name="date" content="$Date$" />
<meta name="copyright" content="Copyright David Abrahams 2004." /> <meta name="copyright" content="Copyright David Abrahams 2004." />
<link rel="stylesheet" href="../../../rst.css" type="text/css" /> <link rel="stylesheet" href="../../../rst.css" type="text/css" />
</head> </head>
@ -25,7 +25,7 @@
<tr><th class="docinfo-name">Organization:</th> <tr><th class="docinfo-name">Organization:</th>
<td><a class="first last reference external" href="http://www.boost-consulting.com">Boost Consulting</a></td></tr> <td><a class="first last reference external" href="http://www.boost-consulting.com">Boost Consulting</a></td></tr>
<tr><th class="docinfo-name">Date:</th> <tr><th class="docinfo-name">Date:</th>
<td>2006-09-11</td></tr> <td>$Date$</td></tr>
<tr><th class="docinfo-name">Copyright:</th> <tr><th class="docinfo-name">Copyright:</th>
<td>Copyright David Abrahams 2004.</td></tr> <td>Copyright David Abrahams 2004.</td></tr>
</tbody> </tbody>
@ -37,7 +37,7 @@
<col class="field-name" /> <col class="field-name" />
<col class="field-body" /> <col class="field-body" />
<tbody valign="top"> <tbody valign="top">
<tr class="field"><th class="field-name">abstract:</th><td class="field-body">Header <tt class="docutils literal"><span class="pre">&lt;boost/iterator/iterator_traits.hpp&gt;</span></tt> provides <tr class="field"><th class="field-name">abstract:</th><td class="field-body">Header <tt class="docutils literal">&lt;boost/iterator/iterator_traits.hpp&gt;</tt> provides
the ability to access an iterator's associated types using the ability to access an iterator's associated types using
MPL-compatible <a class="reference external" href="../../mpl/doc/index.html#metafunctions">metafunctions</a>.</td> MPL-compatible <a class="reference external" href="../../mpl/doc/index.html#metafunctions">metafunctions</a>.</td>
</tr> </tr>
@ -46,15 +46,15 @@ MPL-compatible <a class="reference external" href="../../mpl/doc/index.html#meta
<div class="section" id="overview"> <div class="section" id="overview">
<h1>Overview</h1> <h1>Overview</h1>
<p><tt class="docutils literal"><span class="pre">std::iterator_traits</span></tt> provides access to five associated types <p><tt class="docutils literal"><span class="pre">std::iterator_traits</span></tt> provides access to five associated types
of any iterator: its <tt class="docutils literal"><span class="pre">value_type</span></tt>, <tt class="docutils literal"><span class="pre">reference</span></tt>, <tt class="docutils literal"><span class="pre">pointer</span></tt>, of any iterator: its <tt class="docutils literal">value_type</tt>, <tt class="docutils literal">reference</tt>, <tt class="docutils literal">pointer</tt>,
<tt class="docutils literal"><span class="pre">iterator_category</span></tt>, and <tt class="docutils literal"><span class="pre">difference_type</span></tt>. Unfortunately, <tt class="docutils literal">iterator_category</tt>, and <tt class="docutils literal">difference_type</tt>. Unfortunately,
such a &quot;multi-valued&quot; traits template can be difficult to use in a such a &quot;multi-valued&quot; traits template can be difficult to use in a
metaprogramming context. <tt class="docutils literal"><span class="pre">&lt;boost/iterator/iterator_traits.hpp&gt;</span></tt> metaprogramming context. <tt class="docutils literal">&lt;boost/iterator/iterator_traits.hpp&gt;</tt>
provides access to these types using a standard <a class="reference external" href="../../mpl/doc/index.html#metafunctions">metafunctions</a>.</p> provides access to these types using a standard <a class="reference external" href="../../mpl/doc/index.html#metafunctions">metafunctions</a>.</p>
</div> </div>
<div class="section" id="summary"> <div class="section" id="summary">
<h1>Summary</h1> <h1>Summary</h1>
<p>Header <tt class="docutils literal"><span class="pre">&lt;boost/iterator/iterator_traits.hpp&gt;</span></tt>:</p> <p>Header <tt class="docutils literal">&lt;boost/iterator/iterator_traits.hpp&gt;</tt>:</p>
<pre class="literal-block"> <pre class="literal-block">
template &lt;class Iterator&gt; template &lt;class Iterator&gt;
struct iterator_value struct iterator_value
@ -98,21 +98,6 @@ struct iterator_category
}; };
</pre> </pre>
</div> </div>
<div class="section" id="broken-compiler-notes">
<h1>Broken Compiler Notes</h1>
<p>Because of workarounds in Boost, you may find that these
<a class="reference external" href="../../mpl/doc/index.html#metafunctions">metafunctions</a> actually work better than the facilities provided by
your compiler's standard library.</p>
<p>On compilers that don't support partial specialization, such as
Microsoft Visual C++ 6.0 or 7.0, you may need to manually invoke
<a class="reference external" href="../../type_traits/index.html#transformations">BOOST_BROKEN_COMPILER_TYPE_TRAITS_SPECIALIZATION</a> on the
<tt class="docutils literal"><span class="pre">value_type</span></tt> of pointers that are passed to these metafunctions.</p>
<p>Because of bugs in the implementation of GCC-2.9x, the name of
<tt class="docutils literal"><span class="pre">iterator_category</span></tt> is changed to <tt class="docutils literal"><span class="pre">iterator_category_</span></tt> on that
compiler. A macro, <tt class="docutils literal"><span class="pre">BOOST_ITERATOR_CATEGORY</span></tt>, that expands to
either <tt class="docutils literal"><span class="pre">iterator_category</span></tt> or <tt class="docutils literal"><span class="pre">iterator_category_</span></tt>, as
appropriate to the platform, is provided for portability.</p>
</div>
</div> </div>
<div class="footer"> <div class="footer">
<hr class="footer" /> <hr class="footer" />

0
doc/iterator_traits.pdf Executable file → Normal file
View File

21
doc/iterator_traits.rst Executable file → Normal file
View File

@ -75,24 +75,3 @@ Header ``<boost/iterator/iterator_traits.hpp>``::
detail::iterator_traits<Iterator>::iterator_category detail::iterator_traits<Iterator>::iterator_category
type; type;
}; };
Broken Compiler Notes
=====================
Because of workarounds in Boost, you may find that these
metafunctions_ actually work better than the facilities provided by
your compiler's standard library.
On compilers that don't support partial specialization, such as
Microsoft Visual C++ 6.0 or 7.0, you may need to manually invoke
BOOST_BROKEN_COMPILER_TYPE_TRAITS_SPECIALIZATION_ on the
``value_type`` of pointers that are passed to these metafunctions.
Because of bugs in the implementation of GCC-2.9x, the name of
``iterator_category`` is changed to ``iterator_category_`` on that
compiler. A macro, ``BOOST_ITERATOR_CATEGORY``, that expands to
either ``iterator_category`` or ``iterator_category_``, as
appropriate to the platform, is provided for portability.
.. _BOOST_BROKEN_COMPILER_TYPE_TRAITS_SPECIALIZATION: ../../type_traits/index.html#transformations

0
doc/make_counting_iterator.rst Executable file → Normal file
View File

0
doc/make_filter_iterator.rst Executable file → Normal file
View File

0
doc/make_transform_iterator.rst Executable file → Normal file
View File

0
doc/make_zip_iterator.rst Executable file → Normal file
View File

0
doc/new-iter-concepts.pdf Executable file → Normal file
View File

0
doc/permutation_iterator.pdf Executable file → Normal file
View File

0
doc/pointee.html Executable file → Normal file
View File

0
doc/pointee.pdf Executable file → Normal file
View File

0
doc/pointee.rst Executable file → Normal file
View File

0
doc/pointee_ref.rst Executable file → Normal file
View File

View File

@ -52,21 +52,4 @@ Header `<boost/iterator/iterator_traits.hpp>`:
type; type;
}; };
[h2 Broken Compiler Notes] [endsect]
Because of workarounds in Boost, you may find that these
[@../../mpl/doc/index.html#metafunctions metafunctions] actually work better than the facilities provided by
your compiler's standard library.
On compilers that don't support partial specialization, such as
Microsoft Visual C++ 6.0 or 7.0, you may need to manually invoke
[@../../type_traits/index.html#transformations BOOST_BROKEN_COMPILER_TYPE_TRAITS_SPECIALIZATION] on the
`value_type` of pointers that are passed to these metafunctions.
Because of bugs in the implementation of GCC-2.9x, the name of
`iterator_category` is changed to `iterator_category_` on that
compiler. A macro, `BOOST_ITERATOR_CATEGORY`, that expands to
either `iterator_category` or `iterator_category_`, as
appropriate to the platform, is provided for portability.
[endsect]

View File

@ -49,11 +49,40 @@ proxy references or return the pointee by value. When that
information is needed, call on `indirect_reference`. information is needed, call on `indirect_reference`.
Both of these templates are essential to the correct functioning of Both of these templates are essential to the correct functioning of
[link indirecct `indirect_iterator`]. [link boost_iterator.indirect `indirect_iterator`].
[h2 `minimum_category`]
`minimum_category` takes two iterator categories or two iterator traversal tags
and returns the one that is the weakest (i.e. least advanced). For example:
static_assert(
is_same<
minimum_category<
std::forward_iterator_tag,
std::random_access_iterator_tag
>::type,
std::forward_iterator_tag
>::value,
"Unexpected minimum_category result"
);
[h2 Iterator category and traversal tags manipulation]
The library provides several utilities to simplify conversions between iterator categories
and traversal tags:
* `iterator_category_to_traversal<C>::type` - the metafunction takes an iterator category `C` and returns
the corresponding traversal tag.
* `iterator_traversal<T>::type` - a shorthand for `iterator_category_to_traversal<iterator_category<T>::type>::type`.
* `pure_traversal_tag<T>::type` - the metafunction takes a tag `T` which derives from one of the iterator traversal tags
and returns that traversal tag. `T` may also derive from other tags describing the iterator (e.g. whether this is a `const`-iterator
or not), these additional tags are not considered.
* `pure_iterator_traversal<T>::type` - a shorthand for `pure_traversal_tag<iterator_traversal<T>::type>::type`.
[h2 Reference] [h2 Reference]
[h3 `pointeee`] [h3 `pointee`]
template <class Dereferenceable> template <class Dereferenceable>
struct pointee struct pointee
@ -110,6 +139,77 @@ Both of these templates are essential to the correct functioning of
else else
std::iterator_traits<Dereferenceable>::reference std::iterator_traits<Dereferenceable>::reference
[h3 `minimum_category`]
template <typename C1, typename C2>
struct minimum_category
{
typedef /* see below */ type;
};
[*Requires:] Both `C1` and `C2` shall be standard iterator categories or
iterator traversal tags.
`type` is determined according to the following algorithm, where `c1` is an
object of type `C1` and `c2` is an object of type `C2`:
if (c1 is convertible to c2)
return C2;
else
return C1;
[note The above definition relies on the fact that the more restricting categories
and traversal tags are convertible to the less restricting ones.]
[h3 `iterator_category_to_traversal`]
template <typename C>
struct iterator_category_to_traversal
{
typedef /* see below */ type;
};
[*Requires:] `C` shall be a standard iterator category or an
iterator traversal tag.
If `C` is an iterator traversal tag or convertible to one, `type` equivalent to `C`.
Otherwise, `type` is defined to the closest iterator traversal tag matching `C`.
[h3 `iterator_traversal`]
template <typename Iterator>
struct iterator_traversal
{
typedef typename iterator_category_to_traversal<
typename iterator_category<Iterator>::type
>::type type;
};
[*Requires:] `Iterator` shall be an iterator.
[h3 `pure_traversal_tag`]
template <typename T>
struct pure_traversal_tag
{
typedef /* see below */ type;
};
[*Requires:] `T` shall be convertible to an iterator traversal tag.
`type` is defined to be the most advanced traversal tag `Tag` so that `T` is convertible to `Tag`.
[h3 `pure_iterator_traversal`]
template <typename Iterator>
struct pure_iterator_traversal
{
typedef typename pure_traversal_tag<
typename iterator_traversal<Iterator>::type
>::type type;
};
[*Requires:] `Iterator` shall be an iterator.
[endsect] [endsect]
@ -221,4 +321,4 @@ Iterator Traversal Concepts
[endsect] [endsect]
[endsect] [endsect]

0
doc/reverse_iterator.pdf Executable file → Normal file
View File

0
doc/transform_iterator.pdf Executable file → Normal file
View File

0
doc/transform_iterator_eg.rst Executable file → Normal file
View File

0
doc/zip_iterator.html Executable file → Normal file
View File

0
doc/zip_iterator.pdf Executable file → Normal file
View File

0
doc/zip_iterator.rst Executable file → Normal file
View File

0
doc/zip_iterator_abstract.rst Executable file → Normal file
View File

0
doc/zip_iterator_eg.rst Executable file → Normal file
View File

0
doc/zip_iterator_ref.rst Executable file → Normal file
View File

0
example/node.hpp Executable file → Normal file
View File

0
example/node_iterator1.cpp Executable file → Normal file
View File

0
example/node_iterator1.hpp Executable file → Normal file
View File

0
example/node_iterator2.cpp Executable file → Normal file
View File

0
example/node_iterator2.hpp Executable file → Normal file
View File

0
example/node_iterator3.cpp Executable file → Normal file
View File

0
example/node_iterator3.hpp Executable file → Normal file
View File

View File

@ -14,6 +14,7 @@
#include <iterator> #include <iterator>
namespace boost { namespace boost {
namespace iterators {
template <class UnaryFunction> template <class UnaryFunction>
class function_output_iterator { class function_output_iterator {
@ -33,13 +34,13 @@ namespace boost {
struct output_proxy { struct output_proxy {
output_proxy(UnaryFunction& f) : m_f(f) { } output_proxy(UnaryFunction& f) : m_f(f) { }
template <class T> output_proxy& operator=(const T& value) { template <class T> output_proxy& operator=(const T& value) {
m_f(value); m_f(value);
return *this; return *this;
} }
UnaryFunction& m_f; UnaryFunction& m_f;
}; };
output_proxy operator*() { return output_proxy(m_f); } output_proxy operator*() { return output_proxy(m_f); }
self& operator++() { return *this; } self& operator++() { return *this; }
self& operator++(int) { return *this; } self& operator++(int) { return *this; }
private: private:
UnaryFunction m_f; UnaryFunction m_f;
@ -51,6 +52,11 @@ namespace boost {
return function_output_iterator<UnaryFunction>(f); return function_output_iterator<UnaryFunction>(f);
} }
} // namespace iterators
using iterators::function_output_iterator;
using iterators::make_function_output_iterator;
} // namespace boost } // namespace boost
#endif // BOOST_FUNCTION_OUTPUT_ITERATOR_HPP #endif // BOOST_FUNCTION_OUTPUT_ITERATOR_HPP

View File

@ -17,6 +17,7 @@
#include <boost/ref.hpp> #include <boost/ref.hpp>
namespace boost { namespace boost {
namespace iterators {
template<class Generator> template<class Generator>
class generator_iterator class generator_iterator
@ -33,7 +34,7 @@ class generator_iterator
, single_pass_traversal_tag , single_pass_traversal_tag
, typename Generator::result_type const& , typename Generator::result_type const&
> super_t; > super_t;
public: public:
generator_iterator() {} generator_iterator() {}
generator_iterator(Generator* g) : m_g(g), m_value((*m_g)()) {} generator_iterator(Generator* g) : m_g(g), m_value((*m_g)()) {}
@ -73,8 +74,12 @@ make_generator_iterator(Generator & gen)
return result_t(&gen); return result_t(&gen);
} }
} // namespace iterators
using iterators::generator_iterator;
using iterators::generator_iterator_generator;
using iterators::make_generator_iterator;
} // namespace boost } // namespace boost
#endif // BOOST_ITERATOR_ADAPTOR_GENERATOR_ITERATOR_HPP #endif // BOOST_ITERATOR_ADAPTOR_GENERATOR_ITERATOR_HPP

View File

@ -17,7 +17,7 @@
# include <boost/mpl/eval_if.hpp> # include <boost/mpl/eval_if.hpp>
# include <boost/pointee.hpp> # include <boost/pointee.hpp>
namespace boost { namespace boost {
namespace detail namespace detail
{ {
@ -37,7 +37,7 @@ struct indirect_reference
> >
{ {
}; };
} // namespace boost } // namespace boost
#endif // INDIRECT_REFERENCE_DWA200415_HPP #endif // INDIRECT_REFERENCE_DWA200415_HPP

View File

@ -13,6 +13,7 @@
# include <boost/mpl/eval_if.hpp> # include <boost/mpl/eval_if.hpp>
namespace boost { namespace boost {
namespace iterators {
template < template <
class Incrementable class Incrementable
@ -30,13 +31,13 @@ namespace detail
{ {
// For a while, this wasn't true, but we rely on it below. This is a regression assert. // For a while, this wasn't true, but we rely on it below. This is a regression assert.
BOOST_STATIC_ASSERT(::boost::is_integral<char>::value); BOOST_STATIC_ASSERT(::boost::is_integral<char>::value);
# ifndef BOOST_NO_LIMITS_COMPILE_TIME_CONSTANTS # ifndef BOOST_NO_LIMITS_COMPILE_TIME_CONSTANTS
BOOST_STATIC_CONSTANT(bool, value = std::numeric_limits<T>::is_specialized); BOOST_STATIC_CONSTANT(bool, value = std::numeric_limits<T>::is_specialized);
# else # else
# if !BOOST_WORKAROUND(__BORLANDC__, BOOST_TESTED_AT(0x551)) # if !BOOST_WORKAROUND(__BORLANDC__, BOOST_TESTED_AT(0x551))
BOOST_STATIC_CONSTANT( BOOST_STATIC_CONSTANT(
bool, value = ( bool, value = (
@ -46,20 +47,20 @@ namespace detail
# else # else
BOOST_STATIC_CONSTANT(bool, value = ::boost::is_arithmetic<T>::value); BOOST_STATIC_CONSTANT(bool, value = ::boost::is_arithmetic<T>::value);
# endif # endif
# endif # endif
}; };
template <class T> template <class T>
struct is_numeric struct is_numeric
: mpl::bool_<(::boost::detail::is_numeric_impl<T>::value)> : mpl::bool_<(::boost::iterators::detail::is_numeric_impl<T>::value)>
{}; {};
# if defined(BOOST_HAS_LONG_LONG) # if defined(BOOST_HAS_LONG_LONG)
template <> template <>
struct is_numeric< ::boost::long_long_type> struct is_numeric< ::boost::long_long_type>
: mpl::true_ {}; : mpl::true_ {};
template <> template <>
struct is_numeric< ::boost::ulong_long_type> struct is_numeric< ::boost::ulong_long_type>
: mpl::true_ {}; : mpl::true_ {};
@ -69,7 +70,7 @@ namespace detail
template <> template <>
struct is_numeric<wchar_t> struct is_numeric<wchar_t>
: mpl::true_ {}; : mpl::true_ {};
template <class T> template <class T>
struct numeric_difference struct numeric_difference
{ {
@ -77,7 +78,7 @@ namespace detail
}; };
BOOST_STATIC_ASSERT(is_numeric<int>::value); BOOST_STATIC_ASSERT(is_numeric<int>::value);
template <class Incrementable, class CategoryOrTraversal, class Difference> template <class Incrementable, class CategoryOrTraversal, class Difference>
struct counting_iterator_base struct counting_iterator_base
{ {
@ -89,7 +90,7 @@ namespace detail
, iterator_traversal<Incrementable> , iterator_traversal<Incrementable>
> >
>::type traversal; >::type traversal;
typedef typename detail::ia_dflt_help< typedef typename detail::ia_dflt_help<
Difference Difference
, mpl::eval_if< , mpl::eval_if<
@ -98,7 +99,7 @@ namespace detail
, iterator_difference<Incrementable> , iterator_difference<Incrementable>
> >
>::type difference; >::type difference;
typedef iterator_adaptor< typedef iterator_adaptor<
counting_iterator<Incrementable, CategoryOrTraversal, Difference> // self counting_iterator<Incrementable, CategoryOrTraversal, Difference> // self
, Incrementable // Base , Incrementable // Base
@ -106,7 +107,7 @@ namespace detail
# ifndef BOOST_ITERATOR_REF_CONSTNESS_KILLS_WRITABILITY # ifndef BOOST_ITERATOR_REF_CONSTNESS_KILLS_WRITABILITY
const // MSVC won't strip this. Instead we enable Thomas' const // MSVC won't strip this. Instead we enable Thomas'
// criterion (see boost/iterator/detail/facade_iterator_category.hpp) // criterion (see boost/iterator/detail/facade_iterator_category.hpp)
# endif # endif
, traversal , traversal
, Incrementable const& // reference , Incrementable const& // reference
, difference , difference
@ -136,7 +137,7 @@ namespace detail
{ {
static Difference distance(Incrementable1 x, Incrementable2 y) static Difference distance(Incrementable1 x, Incrementable2 y)
{ {
return numeric_distance(x, y); return boost::detail::numeric_distance(x, y);
} }
}; };
} }
@ -154,14 +155,14 @@ class counting_iterator
typedef typename detail::counting_iterator_base< typedef typename detail::counting_iterator_base<
Incrementable, CategoryOrTraversal, Difference Incrementable, CategoryOrTraversal, Difference
>::type super_t; >::type super_t;
friend class iterator_core_access; friend class iterator_core_access;
public: public:
typedef typename super_t::difference_type difference_type; typedef typename super_t::difference_type difference_type;
counting_iterator() { } counting_iterator() { }
counting_iterator(counting_iterator const& rhs) : super_t(rhs.base()) {} counting_iterator(counting_iterator const& rhs) : super_t(rhs.base()) {}
counting_iterator(Incrementable x) counting_iterator(Incrementable x)
@ -177,10 +178,10 @@ class counting_iterator
) )
: super_t(t.base()) : super_t(t.base())
{} {}
# endif # endif
private: private:
typename super_t::reference dereference() const typename super_t::reference dereference() const
{ {
return this->base_reference(); return this->base_reference();
@ -209,7 +210,11 @@ make_counting_iterator(Incrementable x)
return result_t(x); return result_t(x);
} }
} // namespace iterators
} // namespace boost::iterator using iterators::counting_iterator;
using iterators::make_counting_iterator;
} // namespace boost
#endif // COUNTING_ITERATOR_DWA200348_HPP #endif // COUNTING_ITERATOR_DWA200348_HPP

6
include/boost/iterator/detail/any_conversion_eater.hpp Executable file → Normal file
View File

@ -4,7 +4,9 @@
#ifndef ANY_CONVERSION_EATER_DWA20031117_HPP #ifndef ANY_CONVERSION_EATER_DWA20031117_HPP
# define ANY_CONVERSION_EATER_DWA20031117_HPP # define ANY_CONVERSION_EATER_DWA20031117_HPP
namespace boost { namespace detail { namespace boost {
namespace iterators {
namespace detail {
// This type can be used in traits to "eat" up the one user-defined // This type can be used in traits to "eat" up the one user-defined
// implicit conversion allowed. // implicit conversion allowed.
@ -14,6 +16,6 @@ struct any_conversion_eater
any_conversion_eater(T const&); any_conversion_eater(T const&);
}; };
}} // namespace boost::detail }}} // namespace boost::iterators::detail
#endif // ANY_CONVERSION_EATER_DWA20031117_HPP #endif // ANY_CONVERSION_EATER_DWA20031117_HPP

View File

@ -46,8 +46,7 @@
#endif #endif
#if BOOST_WORKAROUND(BOOST_MSVC, <= 1300) \ #if BOOST_WORKAROUND(__BORLANDC__, BOOST_TESTED_AT(0x5A0)) \
|| BOOST_WORKAROUND(__BORLANDC__, BOOST_TESTED_AT(0x5A0)) \
|| (BOOST_WORKAROUND(BOOST_INTEL_CXX_VERSION, <= 700) && defined(_MSC_VER)) \ || (BOOST_WORKAROUND(BOOST_INTEL_CXX_VERSION, <= 700) && defined(_MSC_VER)) \
|| BOOST_WORKAROUND(__DECCXX_VER, BOOST_TESTED_AT(60590042)) \ || BOOST_WORKAROUND(__DECCXX_VER, BOOST_TESTED_AT(60590042)) \
|| BOOST_WORKAROUND(__SUNPRO_CC, BOOST_TESTED_AT(0x590)) || BOOST_WORKAROUND(__SUNPRO_CC, BOOST_TESTED_AT(0x590))
@ -88,8 +87,7 @@
# define BOOST_NO_IS_CONVERTIBLE // "is_convertible doesn't work for simple types" # define BOOST_NO_IS_CONVERTIBLE // "is_convertible doesn't work for simple types"
#endif #endif
#if BOOST_WORKAROUND(__GNUC__, == 2) \ #if BOOST_WORKAROUND(__GNUC__, == 3) && BOOST_WORKAROUND(__GNUC_MINOR__, < 4) && !defined(__EDG_VERSION__) \
|| BOOST_WORKAROUND(__GNUC__, == 3) && BOOST_WORKAROUND(__GNUC_MINOR__, < 4) && !defined(__EDG_VERSION__) \
|| BOOST_WORKAROUND(__BORLANDC__, BOOST_TESTED_AT(0x551)) || BOOST_WORKAROUND(__BORLANDC__, BOOST_TESTED_AT(0x551))
# define BOOST_NO_IS_CONVERTIBLE_TEMPLATE // The following program fails to compile: # define BOOST_NO_IS_CONVERTIBLE_TEMPLATE // The following program fails to compile:
@ -116,16 +114,9 @@
# define BOOST_NO_STRICT_ITERATOR_INTEROPERABILITY # define BOOST_NO_STRICT_ITERATOR_INTEROPERABILITY
#endif #endif
# if !BOOST_WORKAROUND(BOOST_MSVC, <= 1300) # if BOOST_WORKAROUND(__BORLANDC__, BOOST_TESTED_AT(0x564))
# define BOOST_ARG_DEPENDENT_TYPENAME typename
# else
# define BOOST_ARG_DEPENDENT_TYPENAME
# endif
# if BOOST_WORKAROUND(__GNUC__, == 2) && BOOST_WORKAROUND(__GNUC_MINOR__, BOOST_TESTED_AT(95)) \ // GCC-2.95 (obsolete) eagerly instantiates templated constructors and conversion
|| BOOST_WORKAROUND(__BORLANDC__, BOOST_TESTED_AT(0x564))
// GCC-2.95 eagerly instantiates templated constructors and conversion
// operators in convertibility checks, causing premature errors. // operators in convertibility checks, causing premature errors.
// //
// Borland's problems are harder to diagnose due to lack of an // Borland's problems are harder to diagnose due to lack of an

View File

@ -14,7 +14,6 @@
#undef BOOST_NO_IS_CONVERTIBLE #undef BOOST_NO_IS_CONVERTIBLE
#undef BOOST_NO_IS_CONVERTIBLE_TEMPLATE #undef BOOST_NO_IS_CONVERTIBLE_TEMPLATE
#undef BOOST_NO_STRICT_ITERATOR_INTEROPERABILITY #undef BOOST_NO_STRICT_ITERATOR_INTEROPERABILITY
#undef BOOST_ARG_DEPENDENT_TYPENAME
#undef BOOST_NO_LVALUE_RETURN_DETECTION #undef BOOST_NO_LVALUE_RETURN_DETECTION
#undef BOOST_NO_ONE_WAY_ITERATOR_INTEROP #undef BOOST_NO_ONE_WAY_ITERATOR_INTEROP

View File

@ -35,7 +35,7 @@ namespace boost
typedef T type; typedef T type;
}; };
}; };
// //
// For compilers that don't support "Substitution Failure Is Not An Error" // For compilers that don't support "Substitution Failure Is Not An Error"
// enable_if falls back to always enabled. See comments // enable_if falls back to always enabled. See comments
@ -70,11 +70,8 @@ namespace boost
: enabled<(Cond::value)>::template base<Return> : enabled<(Cond::value)>::template base<Return>
# else # else
: mpl::identity<Return> : mpl::identity<Return>
# endif # endif
{ {
# if BOOST_WORKAROUND(BOOST_MSVC, < 1300)
typedef Return type;
# endif
}; };
} // namespace iterators } // namespace iterators

View File

@ -30,10 +30,13 @@
// iterator_category deduction for iterator_facade // iterator_category deduction for iterator_facade
// //
// forward declaration namespace boost {
namespace boost { struct use_default; } namespace iterators {
namespace boost { namespace detail { // forward declaration
struct use_default;
namespace detail {
struct input_output_iterator_tag struct input_output_iterator_tag
: std::input_iterator_tag : std::input_iterator_tag
@ -63,9 +66,9 @@ struct iterator_writability_disabled
, boost::detail::indirect_traits::is_reference_to_const<Reference> , boost::detail::indirect_traits::is_reference_to_const<Reference>
, is_const<ValueParam> , is_const<ValueParam>
> >
# else # else
: is_const<ValueParam> : is_const<ValueParam>
# endif # endif
{}; {};
@ -96,7 +99,7 @@ struct iterator_facade_default_category
, typename mpl::eval_if< , typename mpl::eval_if<
mpl::and_< mpl::and_<
is_convertible<Traversal, single_pass_traversal_tag> is_convertible<Traversal, single_pass_traversal_tag>
// check for readability // check for readability
, is_convertible<Reference, ValueParam> , is_convertible<Reference, ValueParam>
> >
@ -132,7 +135,6 @@ template <class Category, class Traversal>
struct iterator_category_with_traversal struct iterator_category_with_traversal
: Category, Traversal : Category, Traversal
{ {
# if !BOOST_WORKAROUND(BOOST_MSVC, <= 1300)
// Make sure this isn't used to build any categories where // Make sure this isn't used to build any categories where
// convertibility to Traversal is redundant. Should just use the // convertibility to Traversal is redundant. Should just use the
// Category element in that case. // Category element in that case.
@ -147,8 +149,7 @@ struct iterator_category_with_traversal
BOOST_MPL_ASSERT_NOT((is_iterator_traversal<Category>)); BOOST_MPL_ASSERT_NOT((is_iterator_traversal<Category>));
# if !BOOST_WORKAROUND(BOOST_MSVC, BOOST_TESTED_AT(1310)) # if !BOOST_WORKAROUND(BOOST_MSVC, BOOST_TESTED_AT(1310))
BOOST_MPL_ASSERT((is_iterator_traversal<Traversal>)); BOOST_MPL_ASSERT((is_iterator_traversal<Traversal>));
# endif # endif
# endif
}; };
// Computes an iterator_category tag whose traversal is Traversal and // Computes an iterator_category tag whose traversal is Traversal and
@ -156,14 +157,12 @@ struct iterator_category_with_traversal
template <class Traversal, class ValueParam, class Reference> template <class Traversal, class ValueParam, class Reference>
struct facade_iterator_category_impl struct facade_iterator_category_impl
{ {
# if !BOOST_WORKAROUND(BOOST_MSVC, <= 1300)
BOOST_MPL_ASSERT_NOT((is_iterator_category<Traversal>)); BOOST_MPL_ASSERT_NOT((is_iterator_category<Traversal>));
# endif
typedef typename iterator_facade_default_category< typedef typename iterator_facade_default_category<
Traversal,ValueParam,Reference Traversal,ValueParam,Reference
>::type category; >::type category;
typedef typename mpl::if_< typedef typename mpl::if_<
is_same< is_same<
Traversal Traversal
@ -187,7 +186,7 @@ struct facade_iterator_category
{ {
}; };
}} // namespace boost::detail }}} // namespace boost::iterators::detail
# include <boost/iterator/detail/config_undef.hpp> # include <boost/iterator/detail/config_undef.hpp>

113
include/boost/iterator/detail/minimum_category.hpp Executable file → Normal file
View File

@ -4,113 +4,16 @@
#ifndef MINIMUM_CATEGORY_DWA20031119_HPP #ifndef MINIMUM_CATEGORY_DWA20031119_HPP
# define MINIMUM_CATEGORY_DWA20031119_HPP # define MINIMUM_CATEGORY_DWA20031119_HPP
# include <boost/type_traits/is_convertible.hpp> # include <boost/iterator/minimum_category.hpp>
# include <boost/type_traits/is_same.hpp>
# include <boost/mpl/aux_/lambda_support.hpp> namespace boost {
namespace boost { namespace detail { // This import below (as well as the whole header) is for backward compatibility
// // with boost/token_iterator.hpp. It should be removed as soon as that header is fixed.
// Returns the minimum category type or error_type namespace detail {
// if T1 and T2 are unrelated. using iterators::minimum_category;
// } // namespace detail
// For compilers not supporting is_convertible this only
// works with the new boost return and traversal category
// types. The exact boost _types_ are required. No derived types
// will work.
//
//
template <bool GreaterEqual, bool LessEqual>
struct minimum_category_impl
# if BOOST_WORKAROUND(BOOST_MSVC, < 1300)
{
template <class T1, class T2> struct apply
{
typedef T2 type;
};
typedef void type;
}
# endif
;
template <class T1, class T2> } // namespace boost
struct error_not_related_by_convertibility;
template <>
struct minimum_category_impl<true,false>
{
template <class T1, class T2> struct apply
{
typedef T2 type;
};
};
template <>
struct minimum_category_impl<false,true>
{
template <class T1, class T2> struct apply
{
typedef T1 type;
};
};
template <>
struct minimum_category_impl<true,true>
{
template <class T1, class T2> struct apply
{
BOOST_STATIC_ASSERT((is_same<T1,T2>::value));
typedef T1 type;
};
};
template <>
struct minimum_category_impl<false,false>
{
template <class T1, class T2> struct apply
: error_not_related_by_convertibility<T1,T2>
{
};
};
template <class T1 = mpl::_1, class T2 = mpl::_2>
struct minimum_category
{
typedef minimum_category_impl<
# if BOOST_WORKAROUND(BOOST_MSVC, < 1300) // ETI workaround
is_same<T2,int>::value ||
# endif
::boost::is_convertible<T1,T2>::value
, ::boost::is_convertible<T2,T1>::value
# if BOOST_WORKAROUND(BOOST_MSVC, < 1300) // ETI workaround
|| is_same<T1,int>::value
# endif
> outer;
typedef typename outer::template apply<T1,T2> inner;
typedef typename inner::type type;
BOOST_MPL_AUX_LAMBDA_SUPPORT(2,minimum_category,(T1,T2))
};
template <>
struct minimum_category<mpl::_1,mpl::_2>
{
template <class T1, class T2>
struct apply : minimum_category<T1,T2>
{};
BOOST_MPL_AUX_LAMBDA_SUPPORT_SPEC(2,minimum_category,(mpl::_1,mpl::_2))
};
# if BOOST_WORKAROUND(BOOST_MSVC, < 1300) // ETI workaround
template <>
struct minimum_category<int,int>
{
typedef int type;
};
# endif
}} // namespace boost::detail
#endif // MINIMUM_CATEGORY_DWA20031119_HPP #endif // MINIMUM_CATEGORY_DWA20031119_HPP

View File

@ -1,88 +0,0 @@
// (C) Copyright David Abrahams 2002.
// (C) Copyright Jeremy Siek 2002.
// (C) Copyright Thomas Witt 2002.
// (C) Copyright Jeffrey Lee Hellrung, Jr. 2012.
// 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)
#ifndef BOOST_OPERATOR_BRACKETS_DISPATCH_07102012JLH_HPP
#define BOOST_OPERATOR_BRACKETS_DISPATCH_07102012JLH_HPP
#include <boost/iterator/detail/facade_iterator_category.hpp>
#include <boost/type_traits/is_pod.hpp>
#include <boost/type_traits/remove_const.hpp>
#include <boost/mpl/if.hpp>
namespace boost { namespace detail {
// operator[] must return a proxy in case iterator destruction invalidates
// referents.
// To see why, consider the following implementation of operator[]:
// reference operator[](difference_type n) const
// { return *(*this + n); }
// The problem here is that operator[] would return a reference created from
// a temporary iterator.
template <class Value>
struct operator_brackets_value
{
typedef Value result_type;
template <class Iterator>
static result_type apply(Iterator const & i)
{ return *i; }
};
template <class Iterator, class Reference>
struct operator_brackets_const_proxy
{
class result_type
{
Iterator const m_i;
explicit result_type(Iterator const & i) : m_i(i) { }
friend struct operator_brackets_const_proxy;
void operator=(result_type&);
public:
operator Reference() const { return *m_i; }
};
static result_type apply(Iterator const & i)
{ return result_type(i); }
};
template <class Iterator, class Reference>
struct operator_brackets_proxy
{
class result_type
{
Iterator const m_i;
explicit result_type(Iterator const & i) : m_i(i) { }
friend struct operator_brackets_proxy;
void operator=(result_type&);
public:
operator Reference() const { return *m_i; }
operator_brackets_proxy const & operator=(
typename Iterator::value_type const & x) const
{ *m_i = x; return *this; }
};
static result_type apply(Iterator const & i)
{ return result_type(i); }
};
template <class Iterator, class ValueType, class Reference>
struct operator_brackets_dispatch
{
typedef typename mpl::if_c<
iterator_writability_disabled<ValueType,Reference>::value,
typename mpl::if_c<
boost::is_POD<ValueType>::value,
operator_brackets_value<typename boost::remove_const<ValueType>::type>,
operator_brackets_const_proxy<Iterator,Reference>
>::type,
operator_brackets_proxy<Iterator,Reference>
>::type type;
};
} } // namespace detail / namespace boost
#endif // #ifndef BOOST_OPERATOR_BRACKETS_DISPATCH_07102012JLH_HPP

View File

@ -14,8 +14,9 @@
#include <boost/type_traits/is_class.hpp> #include <boost/type_traits/is_class.hpp>
#include <boost/static_assert.hpp> #include <boost/static_assert.hpp>
namespace boost namespace boost {
{ namespace iterators {
template <class Predicate, class Iterator> template <class Predicate, class Iterator>
class filter_iterator; class filter_iterator;
@ -39,7 +40,7 @@ namespace boost
> type; > type;
}; };
} }
template <class Predicate, class Iterator> template <class Predicate, class Iterator>
class filter_iterator class filter_iterator
: public detail::filter_iterator_base<Predicate, Iterator>::type : public detail::filter_iterator_base<Predicate, Iterator>::type
@ -68,7 +69,7 @@ namespace boost
// Don't allow use of this constructor if Predicate is a // Don't allow use of this constructor if Predicate is a
// function pointer type, since it will be 0. // function pointer type, since it will be 0.
BOOST_STATIC_ASSERT(is_class<Predicate>::value); BOOST_STATIC_ASSERT(is_class<Predicate>::value);
#endif #endif
satisfy_predicate(); satisfy_predicate();
} }
@ -108,28 +109,29 @@ namespace boost
}; };
template <class Predicate, class Iterator> template <class Predicate, class Iterator>
filter_iterator<Predicate,Iterator> inline filter_iterator<Predicate,Iterator>
make_filter_iterator(Predicate f, Iterator x, Iterator end = Iterator()) make_filter_iterator(Predicate f, Iterator x, Iterator end = Iterator())
{ {
return filter_iterator<Predicate,Iterator>(f,x,end); return filter_iterator<Predicate,Iterator>(f,x,end);
} }
template <class Predicate, class Iterator> template <class Predicate, class Iterator>
filter_iterator<Predicate,Iterator> inline filter_iterator<Predicate,Iterator>
make_filter_iterator( make_filter_iterator(
typename iterators::enable_if< typename iterators::enable_if<
is_class<Predicate> is_class<Predicate>
, Iterator , Iterator
>::type x >::type x
, Iterator end = Iterator() , Iterator end = Iterator())
#if BOOST_WORKAROUND(BOOST_MSVC, < 1300)
, Predicate* = 0
#endif
)
{ {
return filter_iterator<Predicate,Iterator>(x,end); return filter_iterator<Predicate,Iterator>(x,end);
} }
} // namespace iterators
using iterators::filter_iterator;
using iterators::make_filter_iterator;
} // namespace boost } // namespace boost
#endif // BOOST_FILTER_ITERATOR_23022003THW_HPP #endif // BOOST_FILTER_ITERATOR_23022003THW_HPP

View File

@ -20,6 +20,8 @@
namespace boost { namespace boost {
namespace iterators {
namespace impl { namespace impl {
template <class Function, class Input> template <class Function, class Input>
@ -33,7 +35,7 @@ namespace boost {
{ {
public: public:
function_input_iterator() {} function_input_iterator() {}
function_input_iterator(Function & f_, Input state_ = Input()) function_input_iterator(Function & f_, Input state_ = Input())
: f(&f_), state(state_) {} : f(&f_), state(state_) {}
void increment() { void increment() {
@ -44,7 +46,7 @@ namespace boost {
++state; ++state;
} }
typename Function::result_type const & typename Function::result_type const &
dereference() const { dereference() const {
return (value ? value : value = (*f)()).get(); return (value ? value : value = (*f)()).get();
} }
@ -109,7 +111,7 @@ namespace boost {
} // namespace impl } // namespace impl
template <class Function, class Input> template <class Function, class Input>
class function_input_iterator class function_input_iterator
: public mpl::if_< : public mpl::if_<
function_types::is_function_pointer<Function>, function_types::is_function_pointer<Function>,
impl::function_pointer_input_iterator<Function,Input>, impl::function_pointer_input_iterator<Function,Input>,
@ -154,7 +156,14 @@ namespace boost {
bool operator==(infinite &) const { return false; }; bool operator==(infinite &) const { return false; };
bool operator==(infinite const &) const { return false; }; bool operator==(infinite const &) const { return false; };
}; };
}
} // namespace iterators
using iterators::function_input_iterator;
using iterators::make_function_input_iterator;
using iterators::infinite;
} // namespace boost
#endif #endif

View File

@ -30,12 +30,13 @@
# include <boost/scoped_ptr.hpp> # include <boost/scoped_ptr.hpp>
# include <boost/mpl/bool.hpp> # include <boost/mpl/bool.hpp>
# include <memory> # include <memory>
#endif #endif
#include <boost/iterator/detail/config_def.hpp> // must be last #include #include <boost/iterator/detail/config_def.hpp> // must be last #include
namespace boost namespace boost {
{ namespace iterators {
template <class Iter, class Value, class Category, class Reference, class Difference> template <class Iter, class Value, class Category, class Reference, class Difference>
class indirect_iterator; class indirect_iterator;
@ -44,8 +45,8 @@ namespace boost
template <class Iter, class Value, class Category, class Reference, class Difference> template <class Iter, class Value, class Category, class Reference, class Difference>
struct indirect_base struct indirect_base
{ {
typedef typename iterator_traits<Iter>::value_type dereferenceable; typedef typename boost::detail::iterator_traits<Iter>::value_type dereferenceable;
typedef iterator_adaptor< typedef iterator_adaptor<
indirect_iterator<Iter, Value, Category, Reference, Difference> indirect_iterator<Iter, Value, Category, Reference, Difference>
, Iter , Iter
@ -69,7 +70,7 @@ namespace boost
struct indirect_base<int, int, int, int, int> {}; struct indirect_base<int, int, int, int, int> {};
} // namespace detail } // namespace detail
template < template <
class Iterator class Iterator
, class Value = use_default , class Value = use_default
@ -107,14 +108,14 @@ namespace boost
: super_t(y.base()) : super_t(y.base())
{} {}
private: private:
typename super_t::reference dereference() const typename super_t::reference dereference() const
{ {
# if BOOST_WORKAROUND(__BORLANDC__, < 0x5A0 ) # if BOOST_WORKAROUND(__BORLANDC__, < 0x5A0 )
return const_cast<super_t::reference>(**this->base()); return const_cast<super_t::reference>(**this->base());
# else # else
return **this->base(); return **this->base();
# endif # endif
} }
}; };
@ -132,6 +133,11 @@ namespace boost
return indirect_iterator<Iter, Traits>(x); return indirect_iterator<Iter, Traits>(x);
} }
} // namespace iterators
using iterators::indirect_iterator;
using iterators::make_indirect_iterator;
} // namespace boost } // namespace boost
#include <boost/iterator/detail/config_undef.hpp> #include <boost/iterator/detail/config_undef.hpp>

View File

@ -14,8 +14,8 @@
# include <boost/iterator/detail/config_def.hpp> // must appear last # include <boost/iterator/detail/config_def.hpp> // must appear last
namespace boost namespace boost {
{ namespace iterators {
// //
// Meta function that determines whether two // Meta function that determines whether two
@ -27,7 +27,7 @@ namespace boost
// standards requirements on constant/mutable container // standards requirements on constant/mutable container
// iterators (23.1 [lib.container.requirements]). // iterators (23.1 [lib.container.requirements]).
// //
// For compilers that don't support is_convertible // For compilers that don't support is_convertible
// is_interoperable gives false positives. See comments // is_interoperable gives false positives. See comments
// on operator implementation for consequences. // on operator implementation for consequences.
// //
@ -40,9 +40,13 @@ namespace boost
is_convertible< A, B > is_convertible< A, B >
, is_convertible< B, A > > , is_convertible< B, A > >
# endif # endif
{ {
}; };
} // namespace iterators
using iterators::is_interoperable;
} // namespace boost } // namespace boost
# include <boost/iterator/detail/config_undef.hpp> # include <boost/iterator/detail/config_undef.hpp>

37
include/boost/iterator/is_lvalue_iterator.hpp Executable file → Normal file
View File

@ -18,7 +18,9 @@
#ifndef BOOST_NO_IS_CONVERTIBLE #ifndef BOOST_NO_IS_CONVERTIBLE
namespace boost { namespace boost {
namespace iterators {
namespace detail namespace detail
{ {
#ifndef BOOST_NO_LVALUE_RETURN_DETECTION #ifndef BOOST_NO_LVALUE_RETURN_DETECTION
@ -26,20 +28,20 @@ namespace detail
// to the expression's result if <expression> is an lvalue, or // to the expression's result if <expression> is an lvalue, or
// not_an_lvalue() otherwise. // not_an_lvalue() otherwise.
struct not_an_lvalue {}; struct not_an_lvalue {};
template <class T> template <class T>
T& lvalue_preserver(T&, int); T& lvalue_preserver(T&, int);
template <class U> template <class U>
not_an_lvalue lvalue_preserver(U const&, ...); not_an_lvalue lvalue_preserver(U const&, ...);
# define BOOST_LVALUE_PRESERVER(expr) detail::lvalue_preserver(expr,0) # define BOOST_LVALUE_PRESERVER(expr) detail::lvalue_preserver(expr,0)
#else #else
# define BOOST_LVALUE_PRESERVER(expr) expr # define BOOST_LVALUE_PRESERVER(expr) expr
#endif #endif
// Guts of is_lvalue_iterator. Value is the iterator's value_type // Guts of is_lvalue_iterator. Value is the iterator's value_type
// and the result is computed in the nested rebind template. // and the result is computed in the nested rebind template.
@ -55,12 +57,12 @@ namespace detail
static char tester(conversion_eater, int); static char tester(conversion_eater, int);
static char (& tester(any_conversion_eater, ...) )[2]; static char (& tester(any_conversion_eater, ...) )[2];
template <class It> template <class It>
struct rebind struct rebind
{ {
static It& x; static It& x;
BOOST_STATIC_CONSTANT( BOOST_STATIC_CONSTANT(
bool bool
, value = ( , value = (
@ -75,7 +77,7 @@ namespace detail
}; };
#undef BOOST_LVALUE_PRESERVER #undef BOOST_LVALUE_PRESERVER
// //
// void specializations to handle std input and output iterators // void specializations to handle std input and output iterators
// //
@ -135,11 +137,16 @@ namespace detail
// Define the trait with full mpl lambda capability and various broken // Define the trait with full mpl lambda capability and various broken
// compiler workarounds // compiler workarounds
BOOST_TT_AUX_BOOL_TRAIT_DEF1( BOOST_TT_AUX_BOOL_TRAIT_DEF1(
is_lvalue_iterator,T,::boost::detail::is_readable_lvalue_iterator_impl<T>::value) is_lvalue_iterator,T,::boost::iterators::detail::is_readable_lvalue_iterator_impl<T>::value)
BOOST_TT_AUX_BOOL_TRAIT_DEF1( BOOST_TT_AUX_BOOL_TRAIT_DEF1(
is_non_const_lvalue_iterator,T,::boost::detail::is_non_const_lvalue_iterator_impl<T>::value) is_non_const_lvalue_iterator,T,::boost::iterators::detail::is_non_const_lvalue_iterator_impl<T>::value)
} // namespace iterators
using iterators::is_lvalue_iterator;
using iterators::is_non_const_lvalue_iterator;
} // namespace boost } // namespace boost
#endif #endif

18
include/boost/iterator/is_readable_iterator.hpp Executable file → Normal file
View File

@ -16,7 +16,9 @@
#ifndef BOOST_NO_IS_CONVERTIBLE #ifndef BOOST_NO_IS_CONVERTIBLE
namespace boost { namespace boost {
namespace iterators {
namespace detail namespace detail
{ {
// Guts of is_readable_iterator. Value is the iterator's value_type // Guts of is_readable_iterator. Value is the iterator's value_type
@ -26,12 +28,12 @@ namespace detail
{ {
static char tester(Value&, int); static char tester(Value&, int);
static char (& tester(any_conversion_eater, ...) )[2]; static char (& tester(any_conversion_eater, ...) )[2];
template <class It> template <class It>
struct rebind struct rebind
{ {
static It& x; static It& x;
BOOST_STATIC_CONSTANT( BOOST_STATIC_CONSTANT(
bool bool
, value = ( , value = (
@ -44,7 +46,7 @@ namespace detail
}; };
#undef BOOST_READABLE_PRESERVER #undef BOOST_READABLE_PRESERVER
// //
// void specializations to handle std input and output iterators // void specializations to handle std input and output iterators
// //
@ -97,8 +99,12 @@ namespace detail
// Define the trait with full mpl lambda capability and various broken // Define the trait with full mpl lambda capability and various broken
// compiler workarounds // compiler workarounds
BOOST_TT_AUX_BOOL_TRAIT_DEF1( BOOST_TT_AUX_BOOL_TRAIT_DEF1(
is_readable_iterator,T,::boost::detail::is_readable_iterator_impl2<T>::value) is_readable_iterator,T,::boost::iterators::detail::is_readable_iterator_impl2<T>::value)
} // namespace iterators
using iterators::is_readable_iterator;
} // namespace boost } // namespace boost
#endif #endif

View File

@ -31,28 +31,33 @@
#include <boost/iterator/iterator_traits.hpp> #include <boost/iterator/iterator_traits.hpp>
namespace boost namespace boost {
{ namespace iterators {
// Used as a default template argument internally, merely to // Used as a default template argument internally, merely to
// indicate "use the default", this can also be passed by users // indicate "use the default", this can also be passed by users
// explicitly in order to specify that the default should be used. // explicitly in order to specify that the default should be used.
struct use_default; struct use_default;
# ifndef BOOST_NO_TEMPLATE_PARTIAL_SPECIALIZATION } // namespace iterators
// the incompleteness of use_default causes massive problems for
// is_convertible (naturally). This workaround is fortunately not using iterators::use_default;
// needed for vc6/vc7.
template<class To> // the incompleteness of use_default causes massive problems for
struct is_convertible<use_default,To> // is_convertible (naturally). This workaround is fortunately not
: mpl::false_ {}; // needed for vc6/vc7.
# endif template<class To>
struct is_convertible<use_default,To>
: mpl::false_ {};
namespace iterators {
namespace detail namespace detail
{ {
// //
// Result type used in enable_if_convertible meta function. // Result type used in enable_if_convertible meta function.
// This can be an incomplete type, as only pointers to // This can be an incomplete type, as only pointers to
// enable_if_convertible< ... >::type are used. // enable_if_convertible< ... >::type are used.
// We could have used void for this, but conversion to // We could have used void for this, but conversion to
// void* is just to easy. // void* is just to easy.
@ -73,7 +78,7 @@ namespace boost
// public iterator_adaptor< adapted_iterator<Iterator>, Iterator > // public iterator_adaptor< adapted_iterator<Iterator>, Iterator >
// { // {
// public: // public:
// //
// ... // ...
// //
// template <class OtherIterator> // template <class OtherIterator>
@ -92,38 +97,23 @@ namespace boost
// and not at the actual instantiation. // and not at the actual instantiation.
// //
// enable_if_interoperable can be safely used in user code. It falls back to // enable_if_interoperable can be safely used in user code. It falls back to
// always enabled for compilers that don't support enable_if or is_convertible. // always enabled for compilers that don't support enable_if or is_convertible.
// There is no need for compiler specific workarounds in user code. // There is no need for compiler specific workarounds in user code.
// //
// The operators implementation relies on boost::is_convertible not returning // The operators implementation relies on boost::is_convertible not returning
// false positives for user/library defined iterator types. See comments // false positives for user/library defined iterator types. See comments
// on operator implementation for consequences. // on operator implementation for consequences.
// //
# if BOOST_WORKAROUND(BOOST_MSVC, <= 1300) # if defined(BOOST_NO_IS_CONVERTIBLE) || defined(BOOST_NO_SFINAE)
template<typename From, typename To>
struct enable_if_convertible
{
typedef typename mpl::if_<
mpl::or_<
is_same<From,To>
, is_convertible<From, To>
>
, boost::detail::enable_type
, int&
>::type type;
};
# elif defined(BOOST_NO_IS_CONVERTIBLE) || defined(BOOST_NO_SFINAE)
template <class From, class To> template <class From, class To>
struct enable_if_convertible struct enable_if_convertible
{ {
typedef boost::detail::enable_type type; typedef boost::iterators::detail::enable_type type;
}; };
# elif BOOST_WORKAROUND(_MSC_FULL_VER, BOOST_TESTED_AT(13102292)) && BOOST_MSVC > 1300 # elif BOOST_WORKAROUND(_MSC_FULL_VER, BOOST_TESTED_AT(13102292))
// For some reason vc7.1 needs us to "cut off" instantiation // For some reason vc7.1 needs us to "cut off" instantiation
// of is_convertible in a few cases. // of is_convertible in a few cases.
template<typename From, typename To> template<typename From, typename To>
@ -133,22 +123,22 @@ namespace boost
is_same<From,To> is_same<From,To>
, is_convertible<From, To> , is_convertible<From, To>
> >
, boost::detail::enable_type , boost::iterators::detail::enable_type
> >
{}; {};
# else # else
template<typename From, typename To> template<typename From, typename To>
struct enable_if_convertible struct enable_if_convertible
: iterators::enable_if< : iterators::enable_if<
is_convertible<From, To> is_convertible<From, To>
, boost::detail::enable_type , boost::iterators::detail::enable_type
> >
{}; {};
# endif # endif
// //
// Default template argument handling for iterator_adaptor // Default template argument handling for iterator_adaptor
// //
@ -180,9 +170,9 @@ namespace boost
{ {
typedef iterator_facade< typedef iterator_facade<
Derived Derived
# ifdef BOOST_ITERATOR_REF_CONSTNESS_KILLS_WRITABILITY # ifdef BOOST_ITERATOR_REF_CONSTNESS_KILLS_WRITABILITY
, typename boost::detail::ia_dflt_help< , typename boost::iterators::detail::ia_dflt_help<
Value Value
, mpl::eval_if< , mpl::eval_if<
is_same<Reference,use_default> is_same<Reference,use_default>
@ -191,17 +181,17 @@ namespace boost
> >
>::type >::type
# else # else
, typename boost::detail::ia_dflt_help< , typename boost::iterators::detail::ia_dflt_help<
Value, iterator_value<Base> Value, iterator_value<Base>
>::type >::type
# endif # endif
, typename boost::detail::ia_dflt_help< , typename boost::iterators::detail::ia_dflt_help<
Traversal Traversal
, iterator_traversal<Base> , iterator_traversal<Base>
>::type >::type
, typename boost::detail::ia_dflt_help< , typename boost::iterators::detail::ia_dflt_help<
Reference Reference
, mpl::eval_if< , mpl::eval_if<
is_same<Value,use_default> is_same<Value,use_default>
@ -210,13 +200,13 @@ namespace boost
> >
>::type >::type
, typename boost::detail::ia_dflt_help< , typename boost::iterators::detail::ia_dflt_help<
Difference, iterator_difference<Base> Difference, iterator_difference<Base>
>::type >::type
> >
type; type;
}; };
// workaround for aC++ CR JAGaf33512 // workaround for aC++ CR JAGaf33512
template <class Tr1, class Tr2> template <class Tr1, class Tr2>
inline void iterator_adaptor_assert_traversal () inline void iterator_adaptor_assert_traversal ()
@ -224,7 +214,7 @@ namespace boost
BOOST_STATIC_ASSERT((is_convertible<Tr1, Tr2>::value)); BOOST_STATIC_ASSERT((is_convertible<Tr1, Tr2>::value));
} }
} }
// //
// Iterator Adaptor // Iterator Adaptor
// //
@ -259,14 +249,14 @@ namespace boost
, class Difference = use_default , class Difference = use_default
> >
class iterator_adaptor class iterator_adaptor
: public boost::detail::iterator_adaptor_base< : public boost::iterators::detail::iterator_adaptor_base<
Derived, Base, Value, Traversal, Reference, Difference Derived, Base, Value, Traversal, Reference, Difference
>::type >::type
{ {
friend class iterator_core_access; friend class iterator_core_access;
protected: protected:
typedef typename boost::detail::iterator_adaptor_base< typedef typename boost::iterators::detail::iterator_adaptor_base<
Derived, Base, Value, Traversal, Reference, Difference Derived, Base, Value, Traversal, Reference, Difference
>::type super_t; >::type super_t;
public: public:
@ -285,7 +275,7 @@ namespace boost
protected: protected:
// for convenience in derived classes // for convenience in derived classes
typedef iterator_adaptor<Derived,Base,Value,Traversal,Reference,Difference> iterator_adaptor_; typedef iterator_adaptor<Derived,Base,Value,Traversal,Reference,Difference> iterator_adaptor_;
// //
// lvalue access to the Base object for Derived // lvalue access to the Base object for Derived
// //
@ -301,13 +291,13 @@ namespace boost
// to prevent temptation for Derived classes to use it, which // to prevent temptation for Derived classes to use it, which
// will often result in an error. Derived classes should use // will often result in an error. Derived classes should use
// base_reference(), above, to get direct access to m_iterator. // base_reference(), above, to get direct access to m_iterator.
// //
typename super_t::reference dereference() const typename super_t::reference dereference() const
{ return *m_iterator; } { return *m_iterator; }
template < template <
class OtherDerived, class OtherIterator, class V, class C, class R, class D class OtherDerived, class OtherIterator, class V, class C, class R, class D
> >
bool equal(iterator_adaptor<OtherDerived, OtherIterator, V, C, R, D> const& x) const bool equal(iterator_adaptor<OtherDerived, OtherIterator, V, C, R, D> const& x) const
{ {
// Maybe readd with same_distance // Maybe readd with same_distance
@ -322,17 +312,17 @@ namespace boost
>::type my_traversal; >::type my_traversal;
# define BOOST_ITERATOR_ADAPTOR_ASSERT_TRAVERSAL(cat) \ # define BOOST_ITERATOR_ADAPTOR_ASSERT_TRAVERSAL(cat) \
boost::detail::iterator_adaptor_assert_traversal<my_traversal, cat>(); boost::iterators::detail::iterator_adaptor_assert_traversal<my_traversal, cat>();
void advance(typename super_t::difference_type n) void advance(typename super_t::difference_type n)
{ {
BOOST_ITERATOR_ADAPTOR_ASSERT_TRAVERSAL(random_access_traversal_tag) BOOST_ITERATOR_ADAPTOR_ASSERT_TRAVERSAL(random_access_traversal_tag)
m_iterator += n; m_iterator += n;
} }
void increment() { ++m_iterator; } void increment() { ++m_iterator; }
void decrement() void decrement()
{ {
BOOST_ITERATOR_ADAPTOR_ASSERT_TRAVERSAL(bidirectional_traversal_tag) BOOST_ITERATOR_ADAPTOR_ASSERT_TRAVERSAL(bidirectional_traversal_tag)
--m_iterator; --m_iterator;
@ -340,7 +330,7 @@ namespace boost
template < template <
class OtherDerived, class OtherIterator, class V, class C, class R, class D class OtherDerived, class OtherIterator, class V, class C, class R, class D
> >
typename super_t::difference_type distance_to( typename super_t::difference_type distance_to(
iterator_adaptor<OtherDerived, OtherIterator, V, C, R, D> const& y) const iterator_adaptor<OtherDerived, OtherIterator, V, C, R, D> const& y) const
{ {
@ -353,11 +343,16 @@ namespace boost
} }
# undef BOOST_ITERATOR_ADAPTOR_ASSERT_TRAVERSAL # undef BOOST_ITERATOR_ADAPTOR_ASSERT_TRAVERSAL
private: // data members private: // data members
Base m_iterator; Base m_iterator;
}; };
} // namespace iterators
using iterators::iterator_adaptor;
using iterators::enable_if_convertible;
} // namespace boost } // namespace boost
#include <boost/iterator/detail/config_undef.hpp> #include <boost/iterator/detail/config_undef.hpp>

View File

@ -20,7 +20,6 @@
#include <boost/concept_archetype.hpp> #include <boost/concept_archetype.hpp>
#include <boost/mpl/aux_/msvc_eti_base.hpp>
#include <boost/mpl/bitand.hpp> #include <boost/mpl/bitand.hpp>
#include <boost/mpl/int.hpp> #include <boost/mpl/int.hpp>
#include <boost/mpl/equal_to.hpp> #include <boost/mpl/equal_to.hpp>
@ -32,6 +31,7 @@
#include <cstddef> #include <cstddef>
namespace boost { namespace boost {
namespace iterators {
template <class Value, class AccessCategory> template <class Value, class AccessCategory>
struct access_archetype; struct access_archetype;
@ -39,7 +39,7 @@ struct access_archetype;
template <class Derived, class Value, class AccessCategory, class TraversalCategory> template <class Derived, class Value, class AccessCategory, class TraversalCategory>
struct traversal_archetype; struct traversal_archetype;
namespace iterator_archetypes namespace archetypes
{ {
enum { enum {
readable_iterator_bit = 1 readable_iterator_bit = 1
@ -51,19 +51,19 @@ namespace iterator_archetypes
// Not quite tags, since dispatching wouldn't work. // Not quite tags, since dispatching wouldn't work.
typedef mpl::int_<readable_iterator_bit>::type readable_iterator_t; typedef mpl::int_<readable_iterator_bit>::type readable_iterator_t;
typedef mpl::int_<writable_iterator_bit>::type writable_iterator_t; typedef mpl::int_<writable_iterator_bit>::type writable_iterator_t;
typedef mpl::int_< typedef mpl::int_<
(readable_iterator_bit|writable_iterator_bit) (readable_iterator_bit|writable_iterator_bit)
>::type readable_writable_iterator_t; >::type readable_writable_iterator_t;
typedef mpl::int_< typedef mpl::int_<
(readable_iterator_bit|lvalue_iterator_bit) (readable_iterator_bit|lvalue_iterator_bit)
>::type readable_lvalue_iterator_t; >::type readable_lvalue_iterator_t;
typedef mpl::int_< typedef mpl::int_<
(lvalue_iterator_bit|writable_iterator_bit) (lvalue_iterator_bit|writable_iterator_bit)
>::type writable_lvalue_iterator_t; >::type writable_lvalue_iterator_t;
typedef mpl::int_<swappable_iterator_bit>::type swappable_iterator_t; typedef mpl::int_<swappable_iterator_bit>::type swappable_iterator_t;
typedef mpl::int_<lvalue_iterator_bit>::type lvalue_iterator_t; typedef mpl::int_<lvalue_iterator_bit>::type lvalue_iterator_t;
@ -119,29 +119,27 @@ namespace detail
template <class Value, class AccessCategory, class TraversalCategory> template <class Value, class AccessCategory, class TraversalCategory>
struct operator_brackets struct operator_brackets
: mpl::aux::msvc_eti_base< : mpl::eval_if<
typename mpl::eval_if< is_convertible<TraversalCategory, random_access_traversal_tag>
is_convertible<TraversalCategory, random_access_traversal_tag> , mpl::eval_if<
, mpl::eval_if< archetypes::has_access<
iterator_archetypes::has_access< AccessCategory
AccessCategory , archetypes::writable_iterator_t
, iterator_archetypes::writable_iterator_t
>
, mpl::identity<writable_operator_brackets<Value> >
, mpl::if_<
iterator_archetypes::has_access<
AccessCategory
, iterator_archetypes::readable_iterator_t
>
, readable_operator_brackets<Value>
, no_operator_brackets
>
> >
, mpl::identity<no_operator_brackets> , mpl::identity<writable_operator_brackets<Value> >
>::type , mpl::if_<
archetypes::has_access<
AccessCategory
, archetypes::readable_iterator_t
>
, readable_operator_brackets<Value>
, no_operator_brackets
>
>
, mpl::identity<no_operator_brackets>
>::type >::type
{}; {};
template <class TraversalCategory> template <class TraversalCategory>
struct traversal_archetype_impl struct traversal_archetype_impl
{ {
@ -154,18 +152,16 @@ namespace detail
template <class Derived, class Value, class TraversalCategory> template <class Derived, class Value, class TraversalCategory>
struct traversal_archetype_ struct traversal_archetype_
: mpl::aux::msvc_eti_base< : traversal_archetype_impl<TraversalCategory>::template archetype<Derived,Value>
typename traversal_archetype_impl<TraversalCategory>::template archetype<Derived,Value>
>::type
{ {
typedef typename typedef typename
traversal_archetype_impl<TraversalCategory>::template archetype<Derived,Value> traversal_archetype_impl<TraversalCategory>::template archetype<Derived,Value>
base; base;
traversal_archetype_() {} traversal_archetype_() {}
traversal_archetype_(ctor_arg arg) traversal_archetype_(ctor_arg arg)
: base(arg) : base(arg)
{} {}
}; };
@ -196,7 +192,7 @@ namespace detail
explicit archetype(ctor_arg arg) explicit archetype(ctor_arg arg)
: traversal_archetype_<Derived, Value, incrementable_traversal_tag>(arg) : traversal_archetype_<Derived, Value, incrementable_traversal_tag>(arg)
{} {}
typedef std::ptrdiff_t difference_type; typedef std::ptrdiff_t difference_type;
}; };
}; };
@ -204,13 +200,7 @@ namespace detail
template <class Derived, class Value> template <class Derived, class Value>
bool operator==(traversal_archetype_<Derived, Value, single_pass_traversal_tag> const&, bool operator==(traversal_archetype_<Derived, Value, single_pass_traversal_tag> const&,
traversal_archetype_<Derived, Value, single_pass_traversal_tag> const&) { return true; } traversal_archetype_<Derived, Value, single_pass_traversal_tag> const&) { return true; }
#if BOOST_WORKAROUND(BOOST_MSVC, <= 1300)
// doesn't seem to pick up != from equality_comparable
template <class Derived, class Value>
bool operator!=(traversal_archetype_<Derived, Value, single_pass_traversal_tag> const&,
traversal_archetype_<Derived, Value, single_pass_traversal_tag> const&) { return true; }
#endif
template <> template <>
struct traversal_archetype_impl<forward_traversal_tag> struct traversal_archetype_impl<forward_traversal_tag>
{ {
@ -218,7 +208,7 @@ namespace detail
struct archetype struct archetype
: public traversal_archetype_<Derived, Value, single_pass_traversal_tag> : public traversal_archetype_<Derived, Value, single_pass_traversal_tag>
{ {
archetype() archetype()
: traversal_archetype_<Derived, Value, single_pass_traversal_tag>(ctor_arg()) : traversal_archetype_<Derived, Value, single_pass_traversal_tag>(ctor_arg())
{} {}
}; };
@ -241,7 +231,7 @@ namespace detail
{ {
template<class Derived, class Value> template<class Derived, class Value>
struct archetype struct archetype
: public traversal_archetype_<Derived, Value, bidirectional_traversal_tag> : public traversal_archetype_<Derived, Value, bidirectional_traversal_tag>
{ {
Derived& operator+=(std::ptrdiff_t) { return static_object<Derived>::get(); } Derived& operator+=(std::ptrdiff_t) { return static_object<Derived>::get(); }
Derived& operator-=(std::ptrdiff_t) { return static_object<Derived>::get(); } Derived& operator-=(std::ptrdiff_t) { return static_object<Derived>::get(); }
@ -300,7 +290,7 @@ namespace detail
template <class> struct undefined; template <class> struct undefined;
template <class AccessCategory> template <class AccessCategory>
struct iterator_access_archetype_impl struct iterator_access_archetype_impl
{ {
@ -309,17 +299,15 @@ struct iterator_access_archetype_impl
template <class Value, class AccessCategory> template <class Value, class AccessCategory>
struct iterator_access_archetype struct iterator_access_archetype
: mpl::aux::msvc_eti_base< : iterator_access_archetype_impl<
typename iterator_access_archetype_impl< AccessCategory
AccessCategory >::template archetype<Value>
>::template archetype<Value>
>::type
{ {
}; };
template <> template <>
struct iterator_access_archetype_impl< struct iterator_access_archetype_impl<
iterator_archetypes::readable_iterator_t archetypes::readable_iterator_t
> >
{ {
template <class Value> template <class Value>
@ -337,15 +325,13 @@ struct iterator_access_archetype_impl<
template <> template <>
struct iterator_access_archetype_impl< struct iterator_access_archetype_impl<
iterator_archetypes::writable_iterator_t archetypes::writable_iterator_t
> >
{ {
template <class Value> template <class Value>
struct archetype struct archetype
{ {
# if !BOOST_WORKAROUND(BOOST_MSVC, <= 1300)
BOOST_STATIC_ASSERT(!is_const<Value>::value); BOOST_STATIC_ASSERT(!is_const<Value>::value);
# endif
typedef void value_type; typedef void value_type;
typedef void reference; typedef void reference;
typedef void pointer; typedef void pointer;
@ -356,13 +342,13 @@ struct iterator_access_archetype_impl<
template <> template <>
struct iterator_access_archetype_impl< struct iterator_access_archetype_impl<
iterator_archetypes::readable_writable_iterator_t archetypes::readable_writable_iterator_t
> >
{ {
template <class Value> template <class Value>
struct archetype struct archetype
: public virtual iterator_access_archetype< : public virtual iterator_access_archetype<
Value, iterator_archetypes::readable_iterator_t Value, archetypes::readable_iterator_t
> >
{ {
typedef detail::read_write_proxy<Value> reference; typedef detail::read_write_proxy<Value> reference;
@ -372,12 +358,12 @@ struct iterator_access_archetype_impl<
}; };
template <> template <>
struct iterator_access_archetype_impl<iterator_archetypes::readable_lvalue_iterator_t> struct iterator_access_archetype_impl<archetypes::readable_lvalue_iterator_t>
{ {
template <class Value> template <class Value>
struct archetype struct archetype
: public virtual iterator_access_archetype< : public virtual iterator_access_archetype<
Value, iterator_archetypes::readable_iterator_t Value, archetypes::readable_iterator_t
> >
{ {
typedef Value& reference; typedef Value& reference;
@ -386,28 +372,26 @@ struct iterator_access_archetype_impl<iterator_archetypes::readable_lvalue_itera
Value* operator->() const { return 0; } Value* operator->() const { return 0; }
}; };
}; };
template <> template <>
struct iterator_access_archetype_impl<iterator_archetypes::writable_lvalue_iterator_t> struct iterator_access_archetype_impl<archetypes::writable_lvalue_iterator_t>
{ {
template <class Value> template <class Value>
struct archetype struct archetype
: public virtual iterator_access_archetype< : public virtual iterator_access_archetype<
Value, iterator_archetypes::readable_lvalue_iterator_t Value, archetypes::readable_lvalue_iterator_t
> >
{ {
# if !BOOST_WORKAROUND(BOOST_MSVC, <= 1300)
BOOST_STATIC_ASSERT((!is_const<Value>::value)); BOOST_STATIC_ASSERT((!is_const<Value>::value));
# endif
}; };
}; };
template <class Value, class AccessCategory, class TraversalCategory> template <class Value, class AccessCategory, class TraversalCategory>
struct iterator_archetype; struct iterator_archetype;
template <class Value, class AccessCategory, class TraversalCategory> template <class Value, class AccessCategory, class TraversalCategory>
struct traversal_archetype_base struct traversal_archetype_base
: detail::operator_brackets< : detail::operator_brackets<
typename remove_cv<Value>::type typename remove_cv<Value>::type
, AccessCategory , AccessCategory
@ -429,12 +413,12 @@ namespace detail
, traversal_archetype_base<Value, AccessCategory, TraversalCategory> , traversal_archetype_base<Value, AccessCategory, TraversalCategory>
{ {
typedef iterator_access_archetype<Value, AccessCategory> access; typedef iterator_access_archetype<Value, AccessCategory> access;
typedef typename detail::facade_iterator_category< typedef typename detail::facade_iterator_category<
TraversalCategory TraversalCategory
, typename mpl::eval_if< , typename mpl::eval_if<
iterator_archetypes::has_access< archetypes::has_access<
AccessCategory, iterator_archetypes::writable_iterator_t AccessCategory, archetypes::writable_iterator_t
> >
, remove_const<Value> , remove_const<Value>
, add_const<Value> , add_const<Value>
@ -467,18 +451,18 @@ struct iterator_archetype
, public detail::iterator_archetype_base< , public detail::iterator_archetype_base<
Value, AccessCategory, TraversalCategory Value, AccessCategory, TraversalCategory
>::workaround_iterator_base >::workaround_iterator_base
# endif # endif
{ {
// Derivation from std::iterator above caused references to nested // Derivation from std::iterator above caused references to nested
// types to be ambiguous, so now we have to redeclare them all // types to be ambiguous, so now we have to redeclare them all
// here. // here.
# if BOOST_WORKAROUND(BOOST_DINKUMWARE_STDLIB, < 310) \ # if BOOST_WORKAROUND(BOOST_DINKUMWARE_STDLIB, < 310) \
|| BOOST_WORKAROUND(_RWSTD_VER, BOOST_TESTED_AT(0x20101)) || BOOST_WORKAROUND(_RWSTD_VER, BOOST_TESTED_AT(0x20101))
typedef detail::iterator_archetype_base< typedef detail::iterator_archetype_base<
Value,AccessCategory,TraversalCategory Value,AccessCategory,TraversalCategory
> base; > base;
typedef typename base::value_type value_type; typedef typename base::value_type value_type;
typedef typename base::reference reference; typedef typename base::reference reference;
typedef typename base::pointer pointer; typedef typename base::pointer pointer;
@ -509,7 +493,17 @@ struct iterator_archetype
# endif # endif
}; };
} // namespace iterators
// Backward compatibility names
namespace iterator_archetypes = iterators::archetypes;
using iterators::access_archetype;
using iterators::traversal_archetype;
using iterators::iterator_archetype;
using iterators::undefined;
using iterators::iterator_access_archetype_impl;
using iterators::traversal_archetype_base;
} // namespace boost } // namespace boost
#endif // BOOST_ITERATOR_ARCHETYPES_HPP #endif // BOOST_ITERATOR_ARCHETYPES_HPP

View File

@ -22,6 +22,7 @@
# include <boost/static_assert.hpp> # include <boost/static_assert.hpp>
namespace boost { namespace boost {
namespace iterators {
// //
// Traversal Categories // Traversal Categories
@ -29,34 +30,34 @@ namespace boost {
struct no_traversal_tag {}; struct no_traversal_tag {};
struct incrementable_traversal_tag struct incrementable_traversal_tag
: no_traversal_tag : no_traversal_tag
{ {
// incrementable_traversal_tag() {} // incrementable_traversal_tag() {}
// incrementable_traversal_tag(std::output_iterator_tag const&) {}; // incrementable_traversal_tag(std::output_iterator_tag const&) {};
}; };
struct single_pass_traversal_tag struct single_pass_traversal_tag
: incrementable_traversal_tag : incrementable_traversal_tag
{ {
// single_pass_traversal_tag() {} // single_pass_traversal_tag() {}
// single_pass_traversal_tag(std::input_iterator_tag const&) {}; // single_pass_traversal_tag(std::input_iterator_tag const&) {};
}; };
struct forward_traversal_tag struct forward_traversal_tag
: single_pass_traversal_tag : single_pass_traversal_tag
{ {
// forward_traversal_tag() {} // forward_traversal_tag() {}
// forward_traversal_tag(std::forward_iterator_tag const&) {}; // forward_traversal_tag(std::forward_iterator_tag const&) {};
}; };
struct bidirectional_traversal_tag struct bidirectional_traversal_tag
: forward_traversal_tag : forward_traversal_tag
{ {
// bidirectional_traversal_tag() {}; // bidirectional_traversal_tag() {};
// bidirectional_traversal_tag(std::bidirectional_iterator_tag const&) {}; // bidirectional_traversal_tag(std::bidirectional_iterator_tag const&) {};
}; };
struct random_access_traversal_tag struct random_access_traversal_tag
: bidirectional_traversal_tag : bidirectional_traversal_tag
{ {
@ -65,7 +66,7 @@ struct random_access_traversal_tag
}; };
namespace detail namespace detail
{ {
// //
// Convert a "strictly old-style" iterator category to a traversal // Convert a "strictly old-style" iterator category to a traversal
// tag. This is broken out into a separate metafunction to reduce // tag. This is broken out into a separate metafunction to reduce
@ -97,51 +98,8 @@ namespace detail
> >
{}; {};
# if BOOST_WORKAROUND(BOOST_MSVC, < 1300)
template <>
struct old_category_to_traversal<int>
{
typedef int type;
};
# endif
template <class Traversal>
struct pure_traversal_tag
: mpl::eval_if<
is_convertible<Traversal,random_access_traversal_tag>
, mpl::identity<random_access_traversal_tag>
, mpl::eval_if<
is_convertible<Traversal,bidirectional_traversal_tag>
, mpl::identity<bidirectional_traversal_tag>
, mpl::eval_if<
is_convertible<Traversal,forward_traversal_tag>
, mpl::identity<forward_traversal_tag>
, mpl::eval_if<
is_convertible<Traversal,single_pass_traversal_tag>
, mpl::identity<single_pass_traversal_tag>
, mpl::eval_if<
is_convertible<Traversal,incrementable_traversal_tag>
, mpl::identity<incrementable_traversal_tag>
, void
>
>
>
>
>
{
};
# if BOOST_WORKAROUND(BOOST_MSVC, < 1300)
template <>
struct pure_traversal_tag<int>
{
typedef int type;
};
# endif
} // namespace detail } // namespace detail
// //
// Convert an iterator category into a traversal tag // Convert an iterator category into a traversal tag
// //
@ -150,7 +108,7 @@ struct iterator_category_to_traversal
: mpl::eval_if< // if already convertible to a traversal tag, we're done. : mpl::eval_if< // if already convertible to a traversal tag, we're done.
is_convertible<Cat,incrementable_traversal_tag> is_convertible<Cat,incrementable_traversal_tag>
, mpl::identity<Cat> , mpl::identity<Cat>
, boost::detail::old_category_to_traversal<Cat> , boost::iterators::detail::old_category_to_traversal<Cat>
> >
{}; {};
@ -181,6 +139,82 @@ struct iterator_traversal<mpl::_>
{}; {};
# endif # endif
//
// Convert an iterator traversal to one of the traversal tags.
//
template <class Traversal>
struct pure_traversal_tag
: mpl::eval_if<
is_convertible<Traversal,random_access_traversal_tag>
, mpl::identity<random_access_traversal_tag>
, mpl::eval_if<
is_convertible<Traversal,bidirectional_traversal_tag>
, mpl::identity<bidirectional_traversal_tag>
, mpl::eval_if<
is_convertible<Traversal,forward_traversal_tag>
, mpl::identity<forward_traversal_tag>
, mpl::eval_if<
is_convertible<Traversal,single_pass_traversal_tag>
, mpl::identity<single_pass_traversal_tag>
, mpl::eval_if<
is_convertible<Traversal,incrementable_traversal_tag>
, mpl::identity<incrementable_traversal_tag>
, void
>
>
>
>
>
{
};
// This import is needed for backward compatibility with Boost.Range:
// boost/range/detail/demote_iterator_traversal_tag.hpp
// It should be removed when that header is fixed.
namespace detail {
using iterators::pure_traversal_tag;
} // namespace detail
//
// Trait to retrieve one of the iterator traversal tags from the iterator category or traversal.
//
template <class Iterator = mpl::_1>
struct pure_iterator_traversal
: pure_traversal_tag<typename iterator_traversal<Iterator>::type>
{};
# ifdef BOOST_MPL_CFG_NO_FULL_LAMBDA_SUPPORT
template <>
struct pure_iterator_traversal<mpl::_1>
{
template <class T>
struct apply : pure_iterator_traversal<T>
{};
};
template <>
struct pure_iterator_traversal<mpl::_>
: pure_iterator_traversal<mpl::_1>
{};
# endif
} // namespace iterators
using iterators::no_traversal_tag;
using iterators::incrementable_traversal_tag;
using iterators::single_pass_traversal_tag;
using iterators::forward_traversal_tag;
using iterators::bidirectional_traversal_tag;
using iterators::random_access_traversal_tag;
using iterators::iterator_category_to_traversal;
using iterators::iterator_traversal;
// This import is needed for backward compatibility with Boost.Range:
// boost/range/detail/demote_iterator_traversal_tag.hpp
// It should be removed when that header is fixed.
namespace detail {
using iterators::pure_traversal_tag;
} // namespace detail
} // namespace boost } // namespace boost
#include <boost/iterator/detail/config_undef.hpp> #include <boost/iterator/detail/config_undef.hpp>

View File

@ -56,7 +56,7 @@ namespace boost_concepts
private: private:
Iterator i; Iterator i;
}; };
template < template <
typename Iterator typename Iterator
, typename ValueType = BOOST_DEDUCED_TYPENAME boost::detail::iterator_traits<Iterator>::value_type , typename ValueType = BOOST_DEDUCED_TYPENAME boost::detail::iterator_traits<Iterator>::value_type
@ -78,7 +78,7 @@ namespace boost_concepts
, typename ValueType = BOOST_DEDUCED_TYPENAME boost::detail::iterator_traits<Iterator>::value_type , typename ValueType = BOOST_DEDUCED_TYPENAME boost::detail::iterator_traits<Iterator>::value_type
> >
struct WritableIteratorConcept : WritableIterator<Iterator,ValueType> {}; struct WritableIteratorConcept : WritableIterator<Iterator,ValueType> {};
BOOST_concept(SwappableIterator,(Iterator)) BOOST_concept(SwappableIterator,(Iterator))
{ {
BOOST_CONCEPT_USAGE(SwappableIterator) BOOST_CONCEPT_USAGE(SwappableIterator)
@ -93,7 +93,7 @@ namespace boost_concepts
BOOST_concept(LvalueIterator,(Iterator)) BOOST_concept(LvalueIterator,(Iterator))
{ {
typedef typename boost::detail::iterator_traits<Iterator>::value_type value_type; typedef typename boost::detail::iterator_traits<Iterator>::value_type value_type;
BOOST_CONCEPT_USAGE(LvalueIterator) BOOST_CONCEPT_USAGE(LvalueIterator)
{ {
value_type& r = const_cast<value_type&>(*i); value_type& r = const_cast<value_type&>(*i);
@ -103,7 +103,7 @@ namespace boost_concepts
Iterator i; Iterator i;
}; };
//=========================================================================== //===========================================================================
// Iterator Traversal Concepts // Iterator Traversal Concepts
@ -145,7 +145,7 @@ namespace boost_concepts
, boost::DefaultConstructible<Iterator> , boost::DefaultConstructible<Iterator>
{ {
typedef typename boost::detail::iterator_traits<Iterator>::difference_type difference_type; typedef typename boost::detail::iterator_traits<Iterator>::difference_type difference_type;
BOOST_MPL_ASSERT((boost::is_integral<difference_type>)); BOOST_MPL_ASSERT((boost::is_integral<difference_type>));
BOOST_MPL_ASSERT_RELATION(std::numeric_limits<difference_type>::is_signed, ==, true); BOOST_MPL_ASSERT_RELATION(std::numeric_limits<difference_type>::is_signed, ==, true);
@ -155,7 +155,7 @@ namespace boost_concepts
, boost::forward_traversal_tag , boost::forward_traversal_tag
> )); > ));
}; };
BOOST_concept(BidirectionalTraversal,(Iterator)) BOOST_concept(BidirectionalTraversal,(Iterator))
: ForwardTraversal<Iterator> : ForwardTraversal<Iterator>
{ {
@ -192,14 +192,14 @@ namespace boost_concepts
i = i - n; i = i - n;
n = i - j; n = i - j;
} }
private: private:
typename BidirectionalTraversal<Iterator>::difference_type n; typename BidirectionalTraversal<Iterator>::difference_type n;
Iterator i, j; Iterator i, j;
}; };
//=========================================================================== //===========================================================================
// Iterator Interoperability // Iterator Interoperability
namespace detail namespace detail
{ {
@ -248,19 +248,10 @@ namespace boost_concepts
BOOST_concept(InteroperableIterator,(Iterator)(ConstIterator)) BOOST_concept(InteroperableIterator,(Iterator)(ConstIterator))
{ {
private: private:
typedef typename boost::detail::pure_traversal_tag< typedef typename boost::iterators::pure_iterator_traversal<Iterator>::type traversal_category;
typename boost::iterator_traversal< typedef typename boost::iterators::pure_iterator_traversal<ConstIterator>::type const_traversal_category;
Iterator
>::type
>::type traversal_category;
typedef typename boost::detail::pure_traversal_tag< public:
typename boost::iterator_traversal<
ConstIterator
>::type
>::type const_traversal_category;
public:
BOOST_CONCEPT_ASSERT((SinglePassIterator<Iterator>)); BOOST_CONCEPT_ASSERT((SinglePassIterator<Iterator>));
BOOST_CONCEPT_ASSERT((SinglePassIterator<ConstIterator>)); BOOST_CONCEPT_ASSERT((SinglePassIterator<ConstIterator>));
@ -271,7 +262,7 @@ namespace boost_concepts
ci = i; ci = i;
} }
private: private:
Iterator i; Iterator i;
ConstIterator ci; ConstIterator ci;

View File

@ -7,9 +7,11 @@
#ifndef BOOST_ITERATOR_FACADE_23022003THW_HPP #ifndef BOOST_ITERATOR_FACADE_23022003THW_HPP
#define BOOST_ITERATOR_FACADE_23022003THW_HPP #define BOOST_ITERATOR_FACADE_23022003THW_HPP
#include <boost/config.hpp>
#include <boost/iterator.hpp> #include <boost/iterator.hpp>
#include <boost/iterator/interoperable.hpp> #include <boost/iterator/interoperable.hpp>
#include <boost/iterator/iterator_traits.hpp> #include <boost/iterator/iterator_traits.hpp>
#include <boost/iterator/iterator_categories.hpp>
#include <boost/iterator/detail/facade_iterator_category.hpp> #include <boost/iterator/detail/facade_iterator_category.hpp>
#include <boost/iterator/detail/enable_if.hpp> #include <boost/iterator/detail/enable_if.hpp>
@ -36,8 +38,9 @@
#include <boost/iterator/detail/config_def.hpp> // this goes last #include <boost/iterator/detail/config_def.hpp> // this goes last
namespace boost namespace boost {
{ namespace iterators {
// This forward declaration is required for the friend declaration // This forward declaration is required for the friend declaration
// in iterator_core_access // in iterator_core_access
template <class I, class V, class TC, class R, class D> class iterator_facade; template <class I, class V, class TC, class R, class D> class iterator_facade;
@ -56,6 +59,12 @@ namespace boost
}; };
}; };
// The type trait checks if the category or traversal is at least as advanced as the specified required traversal
template< typename CategoryOrTraversal, typename Required >
struct is_traversal_at_least :
public boost::is_convertible< typename iterator_category_to_traversal< CategoryOrTraversal >::type, Required >
{};
// //
// enable if for use in operator implementation. // enable if for use in operator implementation.
// //
@ -64,28 +73,31 @@ namespace boost
, class Facade2 , class Facade2
, class Return , class Return
> >
struct enable_if_interoperable struct enable_if_interoperable :
#if BOOST_WORKAROUND(BOOST_MSVC, <= 1300) public boost::iterators::enable_if<
{ is_interoperable< Facade1, Facade2 >
typedef typename mpl::if_< , Return
mpl::or_< >
is_convertible<Facade1, Facade2> {};
, is_convertible<Facade2, Facade1>
> //
// enable if for use in implementation of operators specific for random access traversal.
//
template <
class Facade1
, class Facade2
, class Return
>
struct enable_if_interoperable_and_random_access_traversal :
public boost::iterators::enable_if<
mpl::and_<
is_interoperable< Facade1, Facade2 >
, is_traversal_at_least< typename iterator_category< Facade1 >::type, random_access_traversal_tag >
, is_traversal_at_least< typename iterator_category< Facade2 >::type, random_access_traversal_tag >
>
, Return , Return
, int[3]
>::type type;
};
#else
: ::boost::iterators::enable_if<
mpl::or_<
is_convertible<Facade1, Facade2>
, is_convertible<Facade2, Facade1>
>
, Return
> >
{}; {};
#endif
// //
// Generates associated types for an iterator_facade with the // Generates associated types for an iterator_facade with the
@ -94,7 +106,7 @@ namespace boost
template < template <
class ValueParam class ValueParam
, class CategoryOrTraversal , class CategoryOrTraversal
, class Reference , class Reference
, class Difference , class Difference
> >
struct iterator_facade_types struct iterator_facade_types
@ -102,16 +114,16 @@ namespace boost
typedef typename facade_iterator_category< typedef typename facade_iterator_category<
CategoryOrTraversal, ValueParam, Reference CategoryOrTraversal, ValueParam, Reference
>::type iterator_category; >::type iterator_category;
typedef typename remove_const<ValueParam>::type value_type; typedef typename remove_const<ValueParam>::type value_type;
// Not the real associated pointer type // Not the real associated pointer type
typedef typename mpl::eval_if< typedef typename mpl::eval_if<
boost::detail::iterator_writability_disabled<ValueParam,Reference> boost::iterators::detail::iterator_writability_disabled<ValueParam,Reference>
, add_pointer<const value_type> , add_pointer<const value_type>
, add_pointer<value_type> , add_pointer<value_type>
>::type pointer; >::type pointer;
# if defined(BOOST_NO_TEMPLATE_PARTIAL_SPECIALIZATION) \ # if defined(BOOST_NO_TEMPLATE_PARTIAL_SPECIALIZATION) \
&& (BOOST_WORKAROUND(_STLPORT_VERSION, BOOST_TESTED_AT(0x452)) \ && (BOOST_WORKAROUND(_STLPORT_VERSION, BOOST_TESTED_AT(0x452)) \
|| BOOST_WORKAROUND(BOOST_DINKUMWARE_STDLIB, BOOST_TESTED_AT(310))) \ || BOOST_WORKAROUND(BOOST_DINKUMWARE_STDLIB, BOOST_TESTED_AT(310))) \
@ -157,7 +169,7 @@ namespace boost
private: private:
mutable value_type stored_value; mutable value_type stored_value;
}; };
// //
// In general, we can't determine that such an iterator isn't // In general, we can't determine that such an iterator isn't
// writable -- we also need to store a copy of the old iterator so // writable -- we also need to store a copy of the old iterator so
@ -209,7 +221,7 @@ namespace boost
{ {
return stored_iterator; return stored_iterator;
} }
private: private:
mutable value_type stored_value; mutable value_type stored_value;
Iterator stored_iterator; Iterator stored_iterator;
@ -221,7 +233,7 @@ namespace boost
struct is_non_proxy_reference_impl struct is_non_proxy_reference_impl
{ {
static Reference r; static Reference r;
template <class R> template <class R>
static typename mpl::if_< static typename mpl::if_<
is_convertible< is_convertible<
@ -231,17 +243,17 @@ namespace boost
, char[1] , char[1]
, char[2] , char[2]
>::type& helper(R const&); >::type& helper(R const&);
BOOST_STATIC_CONSTANT(bool, value = sizeof(helper(r)) == 1); BOOST_STATIC_CONSTANT(bool, value = sizeof(helper(r)) == 1);
}; };
template <class Reference, class Value> template <class Reference, class Value>
struct is_non_proxy_reference struct is_non_proxy_reference
: mpl::bool_< : mpl::bool_<
is_non_proxy_reference_impl<Reference, Value>::value is_non_proxy_reference_impl<Reference, Value>::value
> >
{}; {};
# else # else
template <class Reference, class Value> template <class Reference, class Value>
struct is_non_proxy_reference struct is_non_proxy_reference
: is_convertible< : is_convertible<
@ -250,8 +262,8 @@ namespace boost
, Value const volatile* , Value const volatile*
> >
{}; {};
# endif # endif
// A metafunction to choose the result type of postfix ++ // A metafunction to choose the result type of postfix ++
// //
// Because the C++98 input iterator requirements say that *r++ has // Because the C++98 input iterator requirements say that *r++ has
@ -273,7 +285,7 @@ namespace boost
mpl::and_< mpl::and_<
// A proxy is only needed for readable iterators // A proxy is only needed for readable iterators
is_convertible<Reference,Value const&> is_convertible<Reference,Value const&>
// No multipass iterator can have values that disappear // No multipass iterator can have values that disappear
// before positions can be re-visited // before positions can be re-visited
, mpl::not_< , mpl::not_<
@ -325,15 +337,6 @@ namespace boost
} }
}; };
# if BOOST_WORKAROUND(BOOST_MSVC, < 1300)
// Deal with ETI
template<>
struct operator_arrow_dispatch<int, int>
{
typedef int result_type;
};
# endif
// A proxy return type for operator[], needed to deal with // A proxy return type for operator[], needed to deal with
// iterators that may invalidate referents upon destruction. // iterators that may invalidate referents upon destruction.
// Consider the temporary iterator in *(a + n) // Consider the temporary iterator in *(a + n)
@ -378,7 +381,7 @@ namespace boost
> >
> >
{}; {};
template <class Iterator, class Value, class Reference> template <class Iterator, class Value, class Reference>
struct operator_brackets_result struct operator_brackets_result
{ {
@ -408,28 +411,34 @@ namespace boost
: :
# ifdef BOOST_NO_ONE_WAY_ITERATOR_INTEROP # ifdef BOOST_NO_ONE_WAY_ITERATOR_INTEROP
iterator_difference<I1> iterator_difference<I1>
# elif BOOST_WORKAROUND(BOOST_MSVC, < 1300) # else
mpl::if_<
is_convertible<I2,I1>
, typename I1::difference_type
, typename I2::difference_type
>
# else
mpl::eval_if< mpl::eval_if<
is_convertible<I2,I1> is_convertible<I2,I1>
, iterator_difference<I1> , iterator_difference<I1>
, iterator_difference<I2> , iterator_difference<I2>
> >
# endif # endif
{}; {};
}; };
template <
class Derived
, class Value
, class CategoryOrTraversal
, class Reference
, class Difference
, bool IsBidirectionalTraversal
, bool IsRandomAccessTraversal
>
class iterator_facade_base;
} // namespace detail } // namespace detail
// Macros which describe the declarations of binary operators // Macros which describe the declarations of binary operators
# ifdef BOOST_NO_STRICT_ITERATOR_INTEROPERABILITY # ifdef BOOST_NO_STRICT_ITERATOR_INTEROPERABILITY
# define BOOST_ITERATOR_FACADE_INTEROP_HEAD(prefix, op, result_type) \ # define BOOST_ITERATOR_FACADE_INTEROP_HEAD_IMPL(prefix, op, result_type, enabler) \
template < \ template < \
class Derived1, class V1, class TC1, class Reference1, class Difference1 \ class Derived1, class V1, class TC1, class Reference1, class Difference1 \
, class Derived2, class V2, class TC2, class Reference2, class Difference2 \ , class Derived2, class V2, class TC2, class Reference2, class Difference2 \
@ -438,24 +447,33 @@ namespace boost
operator op( \ operator op( \
iterator_facade<Derived1, V1, TC1, Reference1, Difference1> const& lhs \ iterator_facade<Derived1, V1, TC1, Reference1, Difference1> const& lhs \
, iterator_facade<Derived2, V2, TC2, Reference2, Difference2> const& rhs) , iterator_facade<Derived2, V2, TC2, Reference2, Difference2> const& rhs)
# else # else
# define BOOST_ITERATOR_FACADE_INTEROP_HEAD(prefix, op, result_type) \ # define BOOST_ITERATOR_FACADE_INTEROP_HEAD_IMPL(prefix, op, result_type, enabler) \
template < \ template < \
class Derived1, class V1, class TC1, class Reference1, class Difference1 \ class Derived1, class V1, class TC1, class Reference1, class Difference1 \
, class Derived2, class V2, class TC2, class Reference2, class Difference2 \ , class Derived2, class V2, class TC2, class Reference2, class Difference2 \
> \ > \
prefix typename boost::detail::enable_if_interoperable< \ prefix typename enabler< \
Derived1, Derived2 \ Derived1, Derived2 \
, typename mpl::apply2<result_type,Derived1,Derived2>::type \ , typename mpl::apply2<result_type,Derived1,Derived2>::type \
>::type \ >::type \
operator op( \ operator op( \
iterator_facade<Derived1, V1, TC1, Reference1, Difference1> const& lhs \ iterator_facade<Derived1, V1, TC1, Reference1, Difference1> const& lhs \
, iterator_facade<Derived2, V2, TC2, Reference2, Difference2> const& rhs) , iterator_facade<Derived2, V2, TC2, Reference2, Difference2> const& rhs)
# endif # endif
# define BOOST_ITERATOR_FACADE_INTEROP_HEAD(prefix, op, result_type) \
BOOST_ITERATOR_FACADE_INTEROP_HEAD_IMPL(prefix, op, result_type, boost::iterators::detail::enable_if_interoperable)
# define BOOST_ITERATOR_FACADE_INTEROP_RANDOM_ACCESS_HEAD(prefix, op, result_type) \
BOOST_ITERATOR_FACADE_INTEROP_HEAD_IMPL(prefix, op, result_type, boost::iterators::detail::enable_if_interoperable_and_random_access_traversal)
# define BOOST_ITERATOR_FACADE_PLUS_HEAD(prefix,args) \ # define BOOST_ITERATOR_FACADE_PLUS_HEAD(prefix,args) \
template <class Derived, class V, class TC, class R, class D> \ template <class Derived, class V, class TC, class R, class D> \
prefix Derived operator+ args prefix typename boost::iterators::enable_if< \
boost::iterators::detail::is_traversal_at_least< TC, boost::iterators::random_access_traversal_tag >, \
Derived \
>::type operator+ args
// //
// Helper class for granting access to the iterator core interface. // Helper class for granting access to the iterator core interface.
@ -468,41 +486,49 @@ namespace boost
// //
class iterator_core_access class iterator_core_access
{ {
# if defined(BOOST_NO_MEMBER_TEMPLATE_FRIENDS) # if defined(BOOST_NO_MEMBER_TEMPLATE_FRIENDS)
// Tasteless as this may seem, making all members public allows member templates // Tasteless as this may seem, making all members public allows member templates
// to work in the absence of member template friends. // to work in the absence of member template friends.
public: public:
# else # else
template <class I, class V, class TC, class R, class D> friend class iterator_facade; template <class I, class V, class TC, class R, class D> friend class iterator_facade;
template <class I, class V, class TC, class R, class D, bool IsBidirectionalTraversal, bool IsRandomAccessTraversal>
friend class detail::iterator_facade_base;
# define BOOST_ITERATOR_FACADE_RELATION(op) \ # define BOOST_ITERATOR_FACADE_RELATION(op) \
BOOST_ITERATOR_FACADE_INTEROP_HEAD(friend,op, boost::detail::always_bool2); BOOST_ITERATOR_FACADE_INTEROP_HEAD(friend,op, boost::iterators::detail::always_bool2);
BOOST_ITERATOR_FACADE_RELATION(==) BOOST_ITERATOR_FACADE_RELATION(==)
BOOST_ITERATOR_FACADE_RELATION(!=) BOOST_ITERATOR_FACADE_RELATION(!=)
BOOST_ITERATOR_FACADE_RELATION(<)
BOOST_ITERATOR_FACADE_RELATION(>)
BOOST_ITERATOR_FACADE_RELATION(<=)
BOOST_ITERATOR_FACADE_RELATION(>=)
# undef BOOST_ITERATOR_FACADE_RELATION # undef BOOST_ITERATOR_FACADE_RELATION
BOOST_ITERATOR_FACADE_INTEROP_HEAD( # define BOOST_ITERATOR_FACADE_RANDOM_ACCESS_RELATION(op) \
friend, -, boost::detail::choose_difference_type) BOOST_ITERATOR_FACADE_INTEROP_RANDOM_ACCESS_HEAD(friend,op, boost::iterators::detail::always_bool2);
BOOST_ITERATOR_FACADE_RANDOM_ACCESS_RELATION(<)
BOOST_ITERATOR_FACADE_RANDOM_ACCESS_RELATION(>)
BOOST_ITERATOR_FACADE_RANDOM_ACCESS_RELATION(<=)
BOOST_ITERATOR_FACADE_RANDOM_ACCESS_RELATION(>=)
# undef BOOST_ITERATOR_FACADE_RANDOM_ACCESS_RELATION
BOOST_ITERATOR_FACADE_INTEROP_RANDOM_ACCESS_HEAD(
friend, -, boost::iterators::detail::choose_difference_type)
; ;
BOOST_ITERATOR_FACADE_PLUS_HEAD( BOOST_ITERATOR_FACADE_PLUS_HEAD(
friend inline friend inline
, (iterator_facade<Derived, V, TC, R, D> const& , (iterator_facade<Derived, V, TC, R, D> const&
, typename Derived::difference_type) , typename Derived::difference_type)
) )
; ;
BOOST_ITERATOR_FACADE_PLUS_HEAD( BOOST_ITERATOR_FACADE_PLUS_HEAD(
friend inline friend inline
, (typename Derived::difference_type , (typename Derived::difference_type
, iterator_facade<Derived, V, TC, R, D> const&) , iterator_facade<Derived, V, TC, R, D> const&)
) )
; ;
@ -573,11 +599,156 @@ namespace boost
return *static_cast<I const*>(&facade); return *static_cast<I const*>(&facade);
} }
private:
// objects of this class are useless // objects of this class are useless
iterator_core_access(); //undefined BOOST_DELETED_FUNCTION(iterator_core_access())
}; };
namespace detail {
// Implementation for forward traversal iterators
template <
class Derived
, class Value
, class CategoryOrTraversal
, class Reference
, class Difference
>
class iterator_facade_base< Derived, Value, CategoryOrTraversal, Reference, Difference, false, false >
# ifdef BOOST_ITERATOR_FACADE_NEEDS_ITERATOR_BASE
: public boost::iterators::detail::iterator_facade_types<
Value, CategoryOrTraversal, Reference, Difference
>::base
# undef BOOST_ITERATOR_FACADE_NEEDS_ITERATOR_BASE
# endif
{
private:
typedef boost::iterators::detail::iterator_facade_types<
Value, CategoryOrTraversal, Reference, Difference
> associated_types;
typedef boost::iterators::detail::operator_arrow_dispatch<
Reference
, typename associated_types::pointer
> operator_arrow_dispatch_;
public:
typedef typename associated_types::value_type value_type;
typedef Reference reference;
typedef Difference difference_type;
typedef typename operator_arrow_dispatch_::result_type pointer;
typedef typename associated_types::iterator_category iterator_category;
public:
reference operator*() const
{
return iterator_core_access::dereference(this->derived());
}
pointer operator->() const
{
return operator_arrow_dispatch_::apply(*this->derived());
}
Derived& operator++()
{
iterator_core_access::increment(this->derived());
return this->derived();
}
protected:
//
// Curiously Recurring Template interface.
//
Derived& derived()
{
return *static_cast<Derived*>(this);
}
Derived const& derived() const
{
return *static_cast<Derived const*>(this);
}
};
// Implementation for bidirectional traversal iterators
template <
class Derived
, class Value
, class CategoryOrTraversal
, class Reference
, class Difference
>
class iterator_facade_base< Derived, Value, CategoryOrTraversal, Reference, Difference, true, false > :
public iterator_facade_base< Derived, Value, CategoryOrTraversal, Reference, Difference, false, false >
{
public:
Derived& operator--()
{
iterator_core_access::decrement(this->derived());
return this->derived();
}
Derived operator--(int)
{
Derived tmp(this->derived());
--*this;
return tmp;
}
};
// Implementation for random access traversal iterators
template <
class Derived
, class Value
, class CategoryOrTraversal
, class Reference
, class Difference
>
class iterator_facade_base< Derived, Value, CategoryOrTraversal, Reference, Difference, true, true > :
public iterator_facade_base< Derived, Value, CategoryOrTraversal, Reference, Difference, true, false >
{
private:
typedef iterator_facade_base< Derived, Value, CategoryOrTraversal, Reference, Difference, true, false > base_type;
public:
typedef typename base_type::reference reference;
typedef typename base_type::difference_type difference_type;
public:
typename boost::iterators::detail::operator_brackets_result<Derived, Value, reference>::type
operator[](difference_type n) const
{
typedef boost::iterators::detail::use_operator_brackets_proxy<Value, Reference> use_proxy;
return boost::iterators::detail::make_operator_brackets_result<Derived>(
this->derived() + n
, use_proxy()
);
}
Derived& operator+=(difference_type n)
{
iterator_core_access::advance(this->derived(), n);
return this->derived();
}
Derived& operator-=(difference_type n)
{
iterator_core_access::advance(this->derived(), -n);
return this->derived();
}
Derived operator-(difference_type x) const
{
Derived result(this->derived());
return result -= x;
}
};
} // namespace detail
// //
// iterator_facade - use as a public base class for defining new // iterator_facade - use as a public base class for defining new
// standard-conforming iterators. // standard-conforming iterators.
@ -589,151 +760,38 @@ namespace boost
, class Reference = Value& , class Reference = Value&
, class Difference = std::ptrdiff_t , class Difference = std::ptrdiff_t
> >
class iterator_facade class iterator_facade :
# ifdef BOOST_ITERATOR_FACADE_NEEDS_ITERATOR_BASE public detail::iterator_facade_base<
: public boost::detail::iterator_facade_types< Derived,
Value, CategoryOrTraversal, Reference, Difference Value,
>::base CategoryOrTraversal,
# undef BOOST_ITERATOR_FACADE_NEEDS_ITERATOR_BASE Reference,
# endif Difference,
detail::is_traversal_at_least< CategoryOrTraversal, bidirectional_traversal_tag >::value,
detail::is_traversal_at_least< CategoryOrTraversal, random_access_traversal_tag >::value
>
{ {
private: protected:
//
// Curiously Recurring Template interface.
//
Derived& derived()
{
return *static_cast<Derived*>(this);
}
Derived const& derived() const
{
return *static_cast<Derived const*>(this);
}
typedef boost::detail::iterator_facade_types<
Value, CategoryOrTraversal, Reference, Difference
> associated_types;
typedef boost::detail::operator_arrow_dispatch<
Reference
, typename associated_types::pointer
> operator_arrow_dispatch_;
protected:
// For use by derived classes // For use by derived classes
typedef iterator_facade<Derived,Value,CategoryOrTraversal,Reference,Difference> iterator_facade_; typedef iterator_facade<Derived,Value,CategoryOrTraversal,Reference,Difference> iterator_facade_;
public:
typedef typename associated_types::value_type value_type;
typedef Reference reference;
typedef Difference difference_type;
typedef typename operator_arrow_dispatch_::result_type pointer;
typedef typename associated_types::iterator_category iterator_category;
reference operator*() const
{
return iterator_core_access::dereference(this->derived());
}
pointer operator->() const
{
return operator_arrow_dispatch_::apply(*this->derived());
}
typename boost::detail::operator_brackets_result<Derived,Value,reference>::type
operator[](difference_type n) const
{
typedef boost::detail::use_operator_brackets_proxy<Value,Reference> use_proxy;
return boost::detail::make_operator_brackets_result<Derived>(
this->derived() + n
, use_proxy()
);
}
Derived& operator++()
{
iterator_core_access::increment(this->derived());
return this->derived();
}
# if BOOST_WORKAROUND(BOOST_MSVC, < 1300)
typename boost::detail::postfix_increment_result<Derived,Value,Reference,CategoryOrTraversal>::type
operator++(int)
{
typename boost::detail::postfix_increment_result<Derived,Value,Reference,CategoryOrTraversal>::type
tmp(this->derived());
++*this;
return tmp;
}
# endif
Derived& operator--()
{
iterator_core_access::decrement(this->derived());
return this->derived();
}
Derived operator--(int)
{
Derived tmp(this->derived());
--*this;
return tmp;
}
Derived& operator+=(difference_type n)
{
iterator_core_access::advance(this->derived(), n);
return this->derived();
}
Derived& operator-=(difference_type n)
{
iterator_core_access::advance(this->derived(), -n);
return this->derived();
}
Derived operator-(difference_type x) const
{
Derived result(this->derived());
return result -= x;
}
# if BOOST_WORKAROUND(BOOST_MSVC, < 1300)
// 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
}; };
# if !BOOST_WORKAROUND(BOOST_MSVC, < 1300)
template <class I, class V, class TC, class R, class D> template <class I, class V, class TC, class R, class D>
inline typename boost::detail::postfix_increment_result<I,V,R,TC>::type inline typename boost::iterators::detail::postfix_increment_result<I,V,R,TC>::type
operator++( operator++(
iterator_facade<I,V,TC,R,D>& i iterator_facade<I,V,TC,R,D>& i
, int , int
) )
{ {
typename boost::detail::postfix_increment_result<I,V,R,TC>::type typename boost::iterators::detail::postfix_increment_result<I,V,R,TC>::type
tmp(*static_cast<I*>(&i)); tmp(*static_cast<I*>(&i));
++i; ++i;
return tmp; return tmp;
} }
# endif
// //
// Comparison operator implementation. The library supplied operators // Comparison operator implementation. The library supplied operators
// enables the user to provide fully interoperable constant/mutable // enables the user to provide fully interoperable constant/mutable
@ -824,7 +882,7 @@ namespace boost
# define BOOST_ITERATOR_FACADE_RELATION(op, return_prefix, base_op) \ # define BOOST_ITERATOR_FACADE_RELATION(op, return_prefix, base_op) \
BOOST_ITERATOR_FACADE_INTEROP( \ BOOST_ITERATOR_FACADE_INTEROP( \
op \ op \
, boost::detail::always_bool2 \ , boost::iterators::detail::always_bool2 \
, return_prefix \ , return_prefix \
, base_op \ , base_op \
) )
@ -832,21 +890,50 @@ namespace boost
BOOST_ITERATOR_FACADE_RELATION(==, return, equal) BOOST_ITERATOR_FACADE_RELATION(==, return, equal)
BOOST_ITERATOR_FACADE_RELATION(!=, return !, equal) BOOST_ITERATOR_FACADE_RELATION(!=, return !, equal)
BOOST_ITERATOR_FACADE_RELATION(<, return 0 >, distance_from)
BOOST_ITERATOR_FACADE_RELATION(>, return 0 <, distance_from)
BOOST_ITERATOR_FACADE_RELATION(<=, return 0 >=, distance_from)
BOOST_ITERATOR_FACADE_RELATION(>=, return 0 <=, distance_from)
# undef BOOST_ITERATOR_FACADE_RELATION # undef BOOST_ITERATOR_FACADE_RELATION
# define BOOST_ITERATOR_FACADE_INTEROP_RANDOM_ACCESS(op, result_type, return_prefix, base_op) \
BOOST_ITERATOR_FACADE_INTEROP_RANDOM_ACCESS_HEAD(inline, op, result_type) \
{ \
/* For those compilers that do not support enable_if */ \
BOOST_STATIC_ASSERT(( \
is_interoperable< Derived1, Derived2 >::value && \
boost::iterators::detail::is_traversal_at_least< typename iterator_category< Derived1 >::type, random_access_traversal_tag >::value && \
boost::iterators::detail::is_traversal_at_least< typename iterator_category< Derived2 >::type, random_access_traversal_tag >::value \
)); \
return_prefix iterator_core_access::base_op( \
*static_cast<Derived1 const*>(&lhs) \
, *static_cast<Derived2 const*>(&rhs) \
, BOOST_ITERATOR_CONVERTIBLE(Derived2,Derived1) \
); \
}
# define BOOST_ITERATOR_FACADE_RANDOM_ACCESS_RELATION(op, return_prefix, base_op) \
BOOST_ITERATOR_FACADE_INTEROP_RANDOM_ACCESS( \
op \
, boost::iterators::detail::always_bool2 \
, return_prefix \
, base_op \
)
BOOST_ITERATOR_FACADE_RANDOM_ACCESS_RELATION(<, return 0 >, distance_from)
BOOST_ITERATOR_FACADE_RANDOM_ACCESS_RELATION(>, return 0 <, distance_from)
BOOST_ITERATOR_FACADE_RANDOM_ACCESS_RELATION(<=, return 0 >=, distance_from)
BOOST_ITERATOR_FACADE_RANDOM_ACCESS_RELATION(>=, return 0 <=, distance_from)
# undef BOOST_ITERATOR_FACADE_RANDOM_ACCESS_RELATION
// operator- requires an additional part in the static assertion // operator- requires an additional part in the static assertion
BOOST_ITERATOR_FACADE_INTEROP( BOOST_ITERATOR_FACADE_INTEROP_RANDOM_ACCESS(
- -
, boost::detail::choose_difference_type , boost::iterators::detail::choose_difference_type
, return , return
, distance_from , distance_from
) )
# undef BOOST_ITERATOR_FACADE_INTEROP # undef BOOST_ITERATOR_FACADE_INTEROP
# undef BOOST_ITERATOR_FACADE_INTEROP_HEAD # undef BOOST_ITERATOR_FACADE_INTEROP_RANDOM_ACCESS
# define BOOST_ITERATOR_FACADE_PLUS(args) \ # define BOOST_ITERATOR_FACADE_PLUS(args) \
BOOST_ITERATOR_FACADE_PLUS_HEAD(inline, args) \ BOOST_ITERATOR_FACADE_PLUS_HEAD(inline, args) \
@ -855,18 +942,28 @@ namespace boost
return tmp += n; \ return tmp += n; \
} }
BOOST_ITERATOR_FACADE_PLUS(( BOOST_ITERATOR_FACADE_PLUS((
iterator_facade<Derived, V, TC, R, D> const& i iterator_facade<Derived, V, TC, R, D> const& i
, typename Derived::difference_type n , typename Derived::difference_type n
)) ))
BOOST_ITERATOR_FACADE_PLUS(( BOOST_ITERATOR_FACADE_PLUS((
typename Derived::difference_type n typename Derived::difference_type n
, iterator_facade<Derived, V, TC, R, D> const& i , iterator_facade<Derived, V, TC, R, D> const& i
)) ))
# undef BOOST_ITERATOR_FACADE_PLUS # undef BOOST_ITERATOR_FACADE_PLUS
# undef BOOST_ITERATOR_FACADE_PLUS_HEAD # undef BOOST_ITERATOR_FACADE_PLUS_HEAD
# undef BOOST_ITERATOR_FACADE_INTEROP_HEAD
# undef BOOST_ITERATOR_FACADE_INTEROP_RANDOM_ACCESS_HEAD
# undef BOOST_ITERATOR_FACADE_INTEROP_HEAD_IMPL
} // namespace iterators
using iterators::iterator_core_access;
using iterators::iterator_facade;
} // namespace boost } // namespace boost
#include <boost/iterator/detail/config_undef.hpp> #include <boost/iterator/detail/config_undef.hpp>

View File

@ -8,20 +8,12 @@
# include <boost/detail/iterator.hpp> # include <boost/detail/iterator.hpp>
# include <boost/detail/workaround.hpp> # include <boost/detail/workaround.hpp>
namespace boost { namespace boost {
namespace iterators {
// Unfortunately, g++ 2.95.x chokes when we define a class template // Macro for supporting old compilers, no longer needed but kept
// iterator_category which has the same name as its // for backwards compatibility (it was documented).
// std::iterator_category() function, probably due in part to the #define BOOST_ITERATOR_CATEGORY iterator_category
// "std:: is visible globally" hack it uses. Use
// BOOST_ITERATOR_CATEGORY to write code that's portable to older
// GCCs.
# if BOOST_WORKAROUND(__GNUC__, <= 2)
# define BOOST_ITERATOR_CATEGORY iterator_category_
# else
# define BOOST_ITERATOR_CATEGORY iterator_category
# endif
template <class Iterator> template <class Iterator>
@ -29,20 +21,20 @@ struct iterator_value
{ {
typedef typename boost::detail::iterator_traits<Iterator>::value_type type; typedef typename boost::detail::iterator_traits<Iterator>::value_type type;
}; };
template <class Iterator> template <class Iterator>
struct iterator_reference struct iterator_reference
{ {
typedef typename boost::detail::iterator_traits<Iterator>::reference type; typedef typename boost::detail::iterator_traits<Iterator>::reference type;
}; };
template <class Iterator> template <class Iterator>
struct iterator_pointer struct iterator_pointer
{ {
typedef typename boost::detail::iterator_traits<Iterator>::pointer type; typedef typename boost::detail::iterator_traits<Iterator>::pointer type;
}; };
template <class Iterator> template <class Iterator>
struct iterator_difference struct iterator_difference
{ {
@ -50,43 +42,19 @@ struct iterator_difference
}; };
template <class Iterator> template <class Iterator>
struct BOOST_ITERATOR_CATEGORY struct iterator_category
{ {
typedef typename boost::detail::iterator_traits<Iterator>::iterator_category type; typedef typename boost::detail::iterator_traits<Iterator>::iterator_category type;
}; };
# if BOOST_WORKAROUND(BOOST_MSVC, < 1300) } // namespace iterators
template <>
struct iterator_value<int>
{
typedef void type;
};
template <>
struct iterator_reference<int>
{
typedef void type;
};
template <> using iterators::iterator_value;
struct iterator_pointer<int> using iterators::iterator_reference;
{ using iterators::iterator_pointer;
typedef void type; using iterators::iterator_difference;
}; using iterators::iterator_category;
template <>
struct iterator_difference<int>
{
typedef void type;
};
template <>
struct BOOST_ITERATOR_CATEGORY<int>
{
typedef void type;
};
# endif
} // namespace boost::iterator } // namespace boost
#endif // ITERATOR_TRAITS_DWA200347_HPP #endif // ITERATOR_TRAITS_DWA200347_HPP

View File

@ -0,0 +1,95 @@
// Copyright David Abrahams 2003. Use, modification and distribution is
// subject to 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)
#ifndef BOOST_ITERATOR_MINIMUM_CATEGORY_HPP_INCLUDED_
# define BOOST_ITERATOR_MINIMUM_CATEGORY_HPP_INCLUDED_
# include <boost/static_assert.hpp>
# include <boost/type_traits/is_convertible.hpp>
# include <boost/type_traits/is_same.hpp>
# include <boost/mpl/placeholders.hpp>
# include <boost/mpl/aux_/lambda_support.hpp>
namespace boost {
namespace iterators {
namespace detail {
template <bool GreaterEqual, bool LessEqual>
struct minimum_category_impl;
template <class T1, class T2>
struct error_not_related_by_convertibility;
template <>
struct minimum_category_impl<true,false>
{
template <class T1, class T2> struct apply
{
typedef T2 type;
};
};
template <>
struct minimum_category_impl<false,true>
{
template <class T1, class T2> struct apply
{
typedef T1 type;
};
};
template <>
struct minimum_category_impl<true,true>
{
template <class T1, class T2> struct apply
{
BOOST_STATIC_ASSERT((is_same<T1,T2>::value));
typedef T1 type;
};
};
template <>
struct minimum_category_impl<false,false>
{
template <class T1, class T2> struct apply
: error_not_related_by_convertibility<T1,T2>
{
};
};
} // namespace detail
//
// Returns the minimum category type or fails to compile
// if T1 and T2 are unrelated.
//
template <class T1 = mpl::_1, class T2 = mpl::_2>
struct minimum_category
{
typedef boost::iterators::detail::minimum_category_impl<
::boost::is_convertible<T1,T2>::value
, ::boost::is_convertible<T2,T1>::value
> outer;
typedef typename outer::template apply<T1,T2> inner;
typedef typename inner::type type;
BOOST_MPL_AUX_LAMBDA_SUPPORT(2,minimum_category,(T1,T2))
};
template <>
struct minimum_category<mpl::_1,mpl::_2>
{
template <class T1, class T2>
struct apply : minimum_category<T1,T2>
{};
BOOST_MPL_AUX_LAMBDA_SUPPORT_SPEC(2,minimum_category,(mpl::_1,mpl::_2))
};
} // namespace iterators
} // namespace boost
#endif // BOOST_ITERATOR_MINIMUM_CATEGORY_HPP_INCLUDED_

View File

@ -13,28 +13,28 @@
#include <boost/iterator/iterator_adaptor.hpp> #include <boost/iterator/iterator_adaptor.hpp>
namespace boost namespace boost {
{ namespace iterators {
template< class ElementIterator template< class ElementIterator
, class IndexIterator> , class IndexIterator>
class permutation_iterator class permutation_iterator
: public iterator_adaptor< : public iterator_adaptor<
permutation_iterator<ElementIterator, IndexIterator> permutation_iterator<ElementIterator, IndexIterator>
, IndexIterator, typename detail::iterator_traits<ElementIterator>::value_type , IndexIterator, typename boost::detail::iterator_traits<ElementIterator>::value_type
, use_default, typename detail::iterator_traits<ElementIterator>::reference> , use_default, typename boost::detail::iterator_traits<ElementIterator>::reference>
{ {
typedef iterator_adaptor< typedef iterator_adaptor<
permutation_iterator<ElementIterator, IndexIterator> permutation_iterator<ElementIterator, IndexIterator>
, IndexIterator, typename detail::iterator_traits<ElementIterator>::value_type , IndexIterator, typename boost::detail::iterator_traits<ElementIterator>::value_type
, use_default, typename detail::iterator_traits<ElementIterator>::reference> super_t; , use_default, typename boost::detail::iterator_traits<ElementIterator>::reference> super_t;
friend class iterator_core_access; friend class iterator_core_access;
public: public:
permutation_iterator() : m_elt_iter() {} permutation_iterator() : m_elt_iter() {}
explicit permutation_iterator(ElementIterator x, IndexIterator y) explicit permutation_iterator(ElementIterator x, IndexIterator y)
: super_t(y), m_elt_iter(x) {} : super_t(y), m_elt_iter(x) {}
template<class OtherElementIterator, class OtherIndexIterator> template<class OtherElementIterator, class OtherIndexIterator>
@ -54,18 +54,22 @@ private:
template <class,class> friend class permutation_iterator; template <class,class> friend class permutation_iterator;
#else #else
public: public:
#endif #endif
ElementIterator m_elt_iter; ElementIterator m_elt_iter;
}; };
template <class ElementIterator, class IndexIterator> template <class ElementIterator, class IndexIterator>
permutation_iterator<ElementIterator, IndexIterator> inline permutation_iterator<ElementIterator, IndexIterator>
make_permutation_iterator( ElementIterator e, IndexIterator i ) make_permutation_iterator( ElementIterator e, IndexIterator i )
{ {
return permutation_iterator<ElementIterator, IndexIterator>( e, i ); return permutation_iterator<ElementIterator, IndexIterator>( e, i );
} }
} // namespace iterators
using iterators::permutation_iterator;
using iterators::make_permutation_iterator;
} // namespace boost } // namespace boost

View File

@ -11,8 +11,8 @@
#include <boost/iterator.hpp> #include <boost/iterator.hpp>
#include <boost/iterator/iterator_adaptor.hpp> #include <boost/iterator/iterator_adaptor.hpp>
namespace boost namespace boost {
{ namespace iterators {
// //
// //
@ -28,7 +28,7 @@ namespace boost
public: public:
reverse_iterator() {} reverse_iterator() {}
explicit reverse_iterator(Iterator x) explicit reverse_iterator(Iterator x)
: super_t(x) {} : super_t(x) {}
template<class OtherIterator> template<class OtherIterator>
@ -41,7 +41,7 @@ namespace boost
private: private:
typename super_t::reference dereference() const { return *boost::prior(this->base()); } typename super_t::reference dereference() const { return *boost::prior(this->base()); }
void increment() { --this->base_reference(); } void increment() { --this->base_reference(); }
void decrement() { ++this->base_reference(); } void decrement() { ++this->base_reference(); }
@ -59,11 +59,16 @@ namespace boost
}; };
template <class BidirectionalIterator> template <class BidirectionalIterator>
reverse_iterator<BidirectionalIterator> make_reverse_iterator(BidirectionalIterator x) inline reverse_iterator<BidirectionalIterator> make_reverse_iterator(BidirectionalIterator x)
{ {
return reverse_iterator<BidirectionalIterator>(x); return reverse_iterator<BidirectionalIterator>(x);
} }
} // namespace iterators
using iterators::reverse_iterator;
using iterators::make_reverse_iterator;
} // namespace boost } // namespace boost
#endif // BOOST_REVERSE_ITERATOR_23022003THW_HPP #endif // BOOST_REVERSE_ITERATOR_23022003THW_HPP

View File

@ -26,16 +26,17 @@
#if BOOST_WORKAROUND(BOOST_MSVC, BOOST_TESTED_AT(1310)) #if BOOST_WORKAROUND(BOOST_MSVC, BOOST_TESTED_AT(1310))
# include <boost/type_traits/is_base_and_derived.hpp> # include <boost/type_traits/is_base_and_derived.hpp>
#endif #endif
#include <boost/iterator/detail/config_def.hpp> #include <boost/iterator/detail/config_def.hpp>
namespace boost namespace boost {
{ namespace iterators {
template <class UnaryFunction, class Iterator, class Reference = use_default, class Value = use_default> template <class UnaryFunction, class Iterator, class Reference = use_default, class Value = use_default>
class transform_iterator; class transform_iterator;
namespace detail namespace detail
{ {
// Compute the iterator_adaptor instantiation to be used for transform_iterator // Compute the iterator_adaptor instantiation to be used for transform_iterator
template <class UnaryFunc, class Iterator, class Reference, class Value> template <class UnaryFunc, class Iterator, class Reference, class Value>
@ -72,10 +73,10 @@ namespace boost
template <class UnaryFunc, class Iterator, class Reference, class Value> template <class UnaryFunc, class Iterator, class Reference, class Value>
class transform_iterator class transform_iterator
: public boost::detail::transform_iterator_base<UnaryFunc, Iterator, Reference, Value>::type : public boost::iterators::detail::transform_iterator_base<UnaryFunc, Iterator, Reference, Value>::type
{ {
typedef typename typedef typename
boost::detail::transform_iterator_base<UnaryFunc, Iterator, Reference, Value>::type boost::iterators::detail::transform_iterator_base<UnaryFunc, Iterator, Reference, Value>::type
super_t; super_t;
friend class iterator_core_access; friend class iterator_core_access;
@ -95,7 +96,7 @@ namespace boost
// don't provide this constructor if UnaryFunc is a // don't provide this constructor if UnaryFunc is a
// function pointer type, since it will be 0. Too dangerous. // function pointer type, since it will be 0. Too dangerous.
BOOST_STATIC_ASSERT(is_class<UnaryFunc>::value); BOOST_STATIC_ASSERT(is_class<UnaryFunc>::value);
#endif #endif
} }
template < template <
@ -108,7 +109,7 @@ namespace boost
, typename enable_if_convertible<OtherIterator, Iterator>::type* = 0 , typename enable_if_convertible<OtherIterator, Iterator>::type* = 0
#if !BOOST_WORKAROUND(BOOST_MSVC, == 1310) #if !BOOST_WORKAROUND(BOOST_MSVC, == 1310)
, typename enable_if_convertible<OtherUnaryFunction, UnaryFunc>::type* = 0 , typename enable_if_convertible<OtherUnaryFunction, UnaryFunc>::type* = 0
#endif #endif
) )
: super_t(t.base()), m_f(t.functor()) : super_t(t.base()), m_f(t.functor())
{} {}
@ -126,7 +127,7 @@ namespace boost
}; };
template <class UnaryFunc, class Iterator> template <class UnaryFunc, class Iterator>
transform_iterator<UnaryFunc, Iterator> inline transform_iterator<UnaryFunc, Iterator>
make_transform_iterator(Iterator it, UnaryFunc fun) make_transform_iterator(Iterator it, UnaryFunc fun)
{ {
return transform_iterator<UnaryFunc, Iterator>(it, fun); return transform_iterator<UnaryFunc, Iterator>(it, fun);
@ -140,16 +141,9 @@ namespace boost
// function pointer in the iterator be 0, leading to a runtime // function pointer in the iterator be 0, leading to a runtime
// crash. // crash.
template <class UnaryFunc, class Iterator> template <class UnaryFunc, class Iterator>
#if BOOST_WORKAROUND(BOOST_MSVC, <= 1300) inline typename iterators::enable_if<
typename mpl::if_<
#else
typename iterators::enable_if<
#endif
is_class<UnaryFunc> // We should probably find a cheaper test than is_class<> is_class<UnaryFunc> // We should probably find a cheaper test than is_class<>
, transform_iterator<UnaryFunc, Iterator> , transform_iterator<UnaryFunc, Iterator>
#if BOOST_WORKAROUND(BOOST_MSVC, <= 1300)
, int[3]
#endif
>::type >::type
make_transform_iterator(Iterator it) make_transform_iterator(Iterator it)
{ {
@ -158,13 +152,18 @@ namespace boost
#if defined(BOOST_NO_TEMPLATE_PARTIAL_SPECIALIZATION ) && !defined(BOOST_NO_FUNCTION_TEMPLATE_ORDERING) #if defined(BOOST_NO_TEMPLATE_PARTIAL_SPECIALIZATION ) && !defined(BOOST_NO_FUNCTION_TEMPLATE_ORDERING)
template <class Return, class Argument, class Iterator> template <class Return, class Argument, class Iterator>
transform_iterator< Return (*)(Argument), Iterator, Return> inline transform_iterator< Return (*)(Argument), Iterator, Return>
make_transform_iterator(Iterator it, Return (*fun)(Argument)) make_transform_iterator(Iterator it, Return (*fun)(Argument))
{ {
return transform_iterator<Return (*)(Argument), Iterator, Return>(it, fun); return transform_iterator<Return (*)(Argument), Iterator, Return>(it, fun);
} }
#endif #endif
} // namespace iterators
using iterators::transform_iterator;
using iterators::make_transform_iterator;
} // namespace boost } // namespace boost
#include <boost/iterator/detail/config_undef.hpp> #include <boost/iterator/detail/config_undef.hpp>

View File

@ -14,7 +14,7 @@
#include <boost/iterator/iterator_categories.hpp> #include <boost/iterator/iterator_categories.hpp>
#include <boost/detail/iterator.hpp> #include <boost/detail/iterator.hpp>
#include <boost/iterator/detail/minimum_category.hpp> #include <boost/iterator/minimum_category.hpp>
#include <boost/tuple/tuple.hpp> #include <boost/tuple/tuple.hpp>
@ -27,6 +27,7 @@
#include <boost/mpl/aux_/lambda_support.hpp> #include <boost/mpl/aux_/lambda_support.hpp>
namespace boost { namespace boost {
namespace iterators {
// Zip iterator forward declaration for zip_iterator_base // Zip iterator forward declaration for zip_iterator_base
template<typename IteratorTuple> template<typename IteratorTuple>
@ -60,7 +61,7 @@ namespace boost {
{ {
public: public:
advance_iterator(DiffType step) : m_step(step) {} advance_iterator(DiffType step) : m_step(step) {}
template<typename Iterator> template<typename Iterator>
void operator()(Iterator& it) const void operator()(Iterator& it) const
{ it += m_step; } { it += m_step; }
@ -87,9 +88,9 @@ namespace boost {
{ {
template<typename Iterator> template<typename Iterator>
struct apply struct apply
{ {
typedef typename typedef typename
iterator_traits<Iterator>::reference boost::detail::iterator_traits<Iterator>::reference
type; type;
}; };
@ -97,7 +98,7 @@ namespace boost {
typename apply<Iterator>::type operator()(Iterator const& it) typename apply<Iterator>::type operator()(Iterator const& it)
{ return *it; } { return *it; }
}; };
// The namespace tuple_impl_specific provides two meta- // The namespace tuple_impl_specific provides two meta-
// algorithms and two algorithms for tuples. // algorithms and two algorithms for tuples.
@ -108,7 +109,7 @@ namespace boost {
// //
template<typename Tuple, class UnaryMetaFun> template<typename Tuple, class UnaryMetaFun>
struct tuple_meta_transform; struct tuple_meta_transform;
template<typename Tuple, class UnaryMetaFun> template<typename Tuple, class UnaryMetaFun>
struct tuple_meta_transform_impl struct tuple_meta_transform_impl
{ {
@ -119,7 +120,7 @@ namespace boost {
>::type >::type
, typename tuple_meta_transform< , typename tuple_meta_transform<
typename Tuple::tail_type typename Tuple::tail_type
, UnaryMetaFun , UnaryMetaFun
>::type >::type
> type; > type;
}; };
@ -133,14 +134,14 @@ namespace boost {
> >
{ {
}; };
// Meta-accumulate algorithm for tuples. Note: The template // Meta-accumulate algorithm for tuples. Note: The template
// parameter StartType corresponds to the initial value in // parameter StartType corresponds to the initial value in
// ordinary accumulation. // ordinary accumulation.
// //
template<class Tuple, class BinaryMetaFun, class StartType> template<class Tuple, class BinaryMetaFun, class StartType>
struct tuple_meta_accumulate; struct tuple_meta_accumulate;
template< template<
typename Tuple typename Tuple
, class BinaryMetaFun , class BinaryMetaFun
@ -154,7 +155,7 @@ namespace boost {
, typename tuple_meta_accumulate< , typename tuple_meta_accumulate<
typename Tuple::tail_type typename Tuple::tail_type
, BinaryMetaFun , BinaryMetaFun
, StartType , StartType
>::type >::type
>::type type; >::type type;
}; };
@ -166,14 +167,7 @@ namespace boost {
> >
struct tuple_meta_accumulate struct tuple_meta_accumulate
: mpl::eval_if< : mpl::eval_if<
#if BOOST_WORKAROUND(BOOST_MSVC, < 1300)
mpl::or_<
#endif
boost::is_same<Tuple, tuples::null_type> boost::is_same<Tuple, tuples::null_type>
#if BOOST_WORKAROUND(BOOST_MSVC, < 1300)
, boost::is_same<Tuple,int>
>
#endif
, mpl::identity<StartType> , mpl::identity<StartType>
, tuple_meta_accumulate_impl< , tuple_meta_accumulate_impl<
Tuple Tuple
@ -182,7 +176,7 @@ namespace boost {
> >
> >
{ {
}; };
#if defined(BOOST_NO_FUNCTION_TEMPLATE_ORDERING) \ #if defined(BOOST_NO_FUNCTION_TEMPLATE_ORDERING) \
|| ( \ || ( \
@ -190,17 +184,17 @@ namespace boost {
) )
// Not sure why intel's partial ordering fails in this case, but I'm // Not sure why intel's partial ordering fails in this case, but I'm
// assuming int's an MSVC bug-compatibility feature. // assuming int's an MSVC bug-compatibility feature.
# define BOOST_TUPLE_ALGO_DISPATCH # define BOOST_TUPLE_ALGO_DISPATCH
# define BOOST_TUPLE_ALGO(algo) algo##_impl # define BOOST_TUPLE_ALGO(algo) algo##_impl
# define BOOST_TUPLE_ALGO_TERMINATOR , int # define BOOST_TUPLE_ALGO_TERMINATOR , int
# define BOOST_TUPLE_ALGO_RECURSE , ... # define BOOST_TUPLE_ALGO_RECURSE , ...
#else #else
# define BOOST_TUPLE_ALGO(algo) algo # define BOOST_TUPLE_ALGO(algo) algo
# define BOOST_TUPLE_ALGO_TERMINATOR # define BOOST_TUPLE_ALGO_TERMINATOR
# define BOOST_TUPLE_ALGO_RECURSE # define BOOST_TUPLE_ALGO_RECURSE
#endif #endif
// transform algorithm for tuples. The template parameter Fun // transform algorithm for tuples. The template parameter Fun
// must be a unary functor which is also a unary metafunction // must be a unary functor which is also a unary metafunction
// class that computes its return type based on its argument // class that computes its return type based on its argument
@ -218,22 +212,22 @@ namespace boost {
// Arg* operator()(Arg x); // Arg* operator()(Arg x);
// }; // };
template<typename Fun> template<typename Fun>
tuples::null_type BOOST_TUPLE_ALGO(tuple_transform) inline tuples::null_type BOOST_TUPLE_ALGO(tuple_transform)
(tuples::null_type const&, Fun BOOST_TUPLE_ALGO_TERMINATOR) (tuples::null_type const&, Fun BOOST_TUPLE_ALGO_TERMINATOR)
{ return tuples::null_type(); } { return tuples::null_type(); }
template<typename Tuple, typename Fun> template<typename Tuple, typename Fun>
typename tuple_meta_transform< inline typename tuple_meta_transform<
Tuple Tuple
, Fun , Fun
>::type >::type
BOOST_TUPLE_ALGO(tuple_transform)( BOOST_TUPLE_ALGO(tuple_transform)(
const Tuple& t, const Tuple& t,
Fun f Fun f
BOOST_TUPLE_ALGO_RECURSE BOOST_TUPLE_ALGO_RECURSE
) )
{ {
typedef typename tuple_meta_transform< typedef typename tuple_meta_transform<
BOOST_DEDUCED_TYPENAME Tuple::tail_type BOOST_DEDUCED_TYPENAME Tuple::tail_type
, Fun , Fun
@ -244,58 +238,58 @@ namespace boost {
Fun, BOOST_DEDUCED_TYPENAME Tuple::head_type Fun, BOOST_DEDUCED_TYPENAME Tuple::head_type
>::type >::type
, transformed_tail_type , transformed_tail_type
>( >(
f(boost::tuples::get<0>(t)), tuple_transform(t.get_tail(), f) f(boost::tuples::get<0>(t)), tuple_transform(t.get_tail(), f)
); );
} }
#ifdef BOOST_TUPLE_ALGO_DISPATCH #ifdef BOOST_TUPLE_ALGO_DISPATCH
template<typename Tuple, typename Fun> template<typename Tuple, typename Fun>
typename tuple_meta_transform< inline typename tuple_meta_transform<
Tuple Tuple
, Fun , Fun
>::type >::type
tuple_transform( tuple_transform(
const Tuple& t, const Tuple& t,
Fun f Fun f
) )
{ {
return tuple_transform_impl(t, f, 1); return tuple_transform_impl(t, f, 1);
} }
#endif #endif
// for_each algorithm for tuples. // for_each algorithm for tuples.
// //
template<typename Fun> template<typename Fun>
Fun BOOST_TUPLE_ALGO(tuple_for_each)( inline Fun BOOST_TUPLE_ALGO(tuple_for_each)(
tuples::null_type tuples::null_type
, Fun f BOOST_TUPLE_ALGO_TERMINATOR , Fun f BOOST_TUPLE_ALGO_TERMINATOR
) )
{ return f; } { return f; }
template<typename Tuple, typename Fun> template<typename Tuple, typename Fun>
Fun BOOST_TUPLE_ALGO(tuple_for_each)( inline Fun BOOST_TUPLE_ALGO(tuple_for_each)(
Tuple& t Tuple& t
, Fun f BOOST_TUPLE_ALGO_RECURSE) , Fun f BOOST_TUPLE_ALGO_RECURSE)
{ {
f( t.get_head() ); f( t.get_head() );
return tuple_for_each(t.get_tail(), f); return tuple_for_each(t.get_tail(), f);
} }
#ifdef BOOST_TUPLE_ALGO_DISPATCH #ifdef BOOST_TUPLE_ALGO_DISPATCH
template<typename Tuple, typename Fun> template<typename Tuple, typename Fun>
Fun inline Fun
tuple_for_each( tuple_for_each(
Tuple& t, Tuple& t,
Fun f Fun f
) )
{ {
return tuple_for_each_impl(t, f, 1); return tuple_for_each_impl(t, f, 1);
} }
#endif #endif
// Equality of tuples. NOTE: "==" for tuples currently (7/2003) // Equality of tuples. NOTE: "==" for tuples currently (7/2003)
// has problems under some compilers, so I just do my own. // has problems under some compilers, so I just do my own.
// No point in bringing in a bunch of #ifdefs here. This is // No point in bringing in a bunch of #ifdefs here. This is
@ -305,12 +299,9 @@ namespace boost {
{ return true; } { return true; }
template<typename Tuple1, typename Tuple2> template<typename Tuple1, typename Tuple2>
bool tuple_equal( inline bool tuple_equal(Tuple1 const& t1, Tuple2 const& t2)
Tuple1 const& t1, {
Tuple2 const& t2 return t1.get_head() == t2.get_head() &&
)
{
return t1.get_head() == t2.get_head() &&
tuple_equal(t1.get_tail(), t2.get_tail()); tuple_equal(t1.get_tail(), t2.get_tail());
} }
} }
@ -320,7 +311,7 @@ namespace boost {
template<typename Iterator> template<typename Iterator>
struct iterator_reference struct iterator_reference
{ {
typedef typename iterator_traits<Iterator>::reference type; typedef typename boost::detail::iterator_traits<Iterator>::reference type;
}; };
#ifdef BOOST_MPL_CFG_NO_FULL_LAMBDA_SUPPORT #ifdef BOOST_MPL_CFG_NO_FULL_LAMBDA_SUPPORT
@ -336,14 +327,14 @@ namespace boost {
struct apply : iterator_reference<T> {}; struct apply : iterator_reference<T> {};
}; };
#endif #endif
// Metafunction to obtain the type of the tuple whose element types // Metafunction to obtain the type of the tuple whose element types
// are the reference types of an iterator tuple. // are the reference types of an iterator tuple.
// //
template<typename IteratorTuple> template<typename IteratorTuple>
struct tuple_of_references struct tuple_of_references
: tuple_impl_specific::tuple_meta_transform< : tuple_impl_specific::tuple_meta_transform<
IteratorTuple, IteratorTuple,
iterator_reference<mpl::_1> iterator_reference<mpl::_1>
> >
{ {
@ -359,7 +350,7 @@ namespace boost {
IteratorTuple IteratorTuple
, pure_traversal_tag<iterator_traversal<> > , pure_traversal_tag<iterator_traversal<> >
>::type tuple_of_traversal_tags; >::type tuple_of_traversal_tags;
typedef typename tuple_impl_specific::tuple_meta_accumulate< typedef typename tuple_impl_specific::tuple_meta_accumulate<
tuple_of_traversal_tags tuple_of_traversal_tags
, minimum_category<> , minimum_category<>
@ -367,14 +358,6 @@ namespace boost {
>::type type; >::type type;
}; };
#if BOOST_WORKAROUND(BOOST_MSVC, < 1300) // ETI workaround
template <>
struct minimum_traversal_category_in_iterator_tuple<int>
{
typedef int type;
};
#endif
// We need to call tuple_meta_accumulate with mpl::and_ as the // We need to call tuple_meta_accumulate with mpl::and_ as the
// accumulating functor. To this end, we need to wrap it into // accumulating functor. To this end, we need to wrap it into
// a struct that has exactly two arguments (that is, template // a struct that has exactly two arguments (that is, template
@ -385,7 +368,7 @@ namespace boost {
: mpl::and_<Arg1, Arg2> : mpl::and_<Arg1, Arg2>
{ {
}; };
# ifdef BOOST_MPL_CFG_NO_FULL_LAMBDA_SUPPORT # ifdef BOOST_MPL_CFG_NO_FULL_LAMBDA_SUPPORT
// Hack because BOOST_MPL_AUX_LAMBDA_SUPPORT doesn't seem to work // Hack because BOOST_MPL_AUX_LAMBDA_SUPPORT doesn't seem to work
// out well. In this case I think it's an MPL bug // out well. In this case I think it's an MPL bug
@ -396,13 +379,13 @@ namespace boost {
struct apply : mpl::and_<A1,A2> struct apply : mpl::and_<A1,A2>
{}; {};
}; };
# endif # endif
/////////////////////////////////////////////////////////////////// ///////////////////////////////////////////////////////////////////
// //
// Class zip_iterator_base // Class zip_iterator_base
// //
// Builds and exposes the iterator facade type from which the zip // Builds and exposes the iterator facade type from which the zip
// iterator will be derived. // iterator will be derived.
// //
template<typename IteratorTuple> template<typename IteratorTuple>
@ -411,30 +394,30 @@ namespace boost {
private: private:
// Reference type is the type of the tuple obtained from the // Reference type is the type of the tuple obtained from the
// iterators' reference types. // iterators' reference types.
typedef typename typedef typename
detail::tuple_of_references<IteratorTuple>::type reference; detail::tuple_of_references<IteratorTuple>::type reference;
// Value type is the same as reference type. // Value type is the same as reference type.
typedef reference value_type; typedef reference value_type;
// Difference type is the first iterator's difference type // Difference type is the first iterator's difference type
typedef typename iterator_traits< typedef typename boost::detail::iterator_traits<
typename tuples::element<0, IteratorTuple>::type typename tuples::element<0, IteratorTuple>::type
>::difference_type difference_type; >::difference_type difference_type;
// Traversal catetgory is the minimum traversal category in the // Traversal catetgory is the minimum traversal category in the
// iterator tuple. // iterator tuple.
typedef typename typedef typename
detail::minimum_traversal_category_in_iterator_tuple< detail::minimum_traversal_category_in_iterator_tuple<
IteratorTuple IteratorTuple
>::type traversal_category; >::type traversal_category;
public: public:
// The iterator facade type from which the zip iterator will // The iterator facade type from which the zip iterator will
// be derived. // be derived.
typedef iterator_facade< typedef iterator_facade<
zip_iterator<IteratorTuple>, zip_iterator<IteratorTuple>,
value_type, value_type,
traversal_category, traversal_category,
reference, reference,
difference_type difference_type
@ -447,34 +430,34 @@ namespace boost {
typedef int type; typedef int type;
}; };
} }
///////////////////////////////////////////////////////////////////// /////////////////////////////////////////////////////////////////////
// //
// zip_iterator class definition // zip_iterator class definition
// //
template<typename IteratorTuple> template<typename IteratorTuple>
class zip_iterator : class zip_iterator :
public detail::zip_iterator_base<IteratorTuple>::type public detail::zip_iterator_base<IteratorTuple>::type
{ {
// Typedef super_t as our base class. // Typedef super_t as our base class.
typedef typename typedef typename
detail::zip_iterator_base<IteratorTuple>::type super_t; detail::zip_iterator_base<IteratorTuple>::type super_t;
// iterator_core_access is the iterator's best friend. // iterator_core_access is the iterator's best friend.
friend class iterator_core_access; friend class iterator_core_access;
public: public:
// Construction // Construction
// ============ // ============
// Default constructor // Default constructor
zip_iterator() { } zip_iterator() { }
// Constructor from iterator tuple // Constructor from iterator tuple
zip_iterator(IteratorTuple iterator_tuple) zip_iterator(IteratorTuple iterator_tuple)
: m_iterator_tuple(iterator_tuple) : m_iterator_tuple(iterator_tuple)
{ } { }
// Copy constructor // Copy constructor
@ -493,15 +476,15 @@ namespace boost {
{ return m_iterator_tuple; } { return m_iterator_tuple; }
private: private:
// Implementation of Iterator Operations // Implementation of Iterator Operations
// ===================================== // =====================================
// Dereferencing returns a tuple built from the dereferenced // Dereferencing returns a tuple built from the dereferenced
// iterators in the iterator tuple. // iterators in the iterator tuple.
typename super_t::reference dereference() const typename super_t::reference dereference() const
{ {
return detail::tuple_impl_specific::tuple_transform( return detail::tuple_impl_specific::tuple_transform(
get_iterator_tuple(), get_iterator_tuple(),
detail::dereference_iterator() detail::dereference_iterator()
); );
@ -517,7 +500,7 @@ namespace boost {
// under several compilers. No point in bringing in a bunch // under several compilers. No point in bringing in a bunch
// of #ifdefs here. // of #ifdefs here.
// //
template<typename OtherIteratorTuple> template<typename OtherIteratorTuple>
bool equal(const zip_iterator<OtherIteratorTuple>& other) const bool equal(const zip_iterator<OtherIteratorTuple>& other) const
{ {
return detail::tuple_impl_specific::tuple_equal( return detail::tuple_impl_specific::tuple_equal(
@ -529,7 +512,7 @@ namespace boost {
// Advancing a zip iterator means to advance all iterators in the // Advancing a zip iterator means to advance all iterators in the
// iterator tuple. // iterator tuple.
void advance(typename super_t::difference_type n) void advance(typename super_t::difference_type n)
{ {
detail::tuple_impl_specific::tuple_for_each( detail::tuple_impl_specific::tuple_for_each(
m_iterator_tuple, m_iterator_tuple,
detail::advance_iterator<BOOST_DEDUCED_TYPENAME super_t::difference_type>(n) detail::advance_iterator<BOOST_DEDUCED_TYPENAME super_t::difference_type>(n)
@ -538,48 +521,53 @@ namespace boost {
// Incrementing a zip iterator means to increment all iterators in // Incrementing a zip iterator means to increment all iterators in
// the iterator tuple. // the iterator tuple.
void increment() void increment()
{ {
detail::tuple_impl_specific::tuple_for_each( detail::tuple_impl_specific::tuple_for_each(
m_iterator_tuple, m_iterator_tuple,
detail::increment_iterator() detail::increment_iterator()
); );
} }
// Decrementing a zip iterator means to decrement all iterators in // Decrementing a zip iterator means to decrement all iterators in
// the iterator tuple. // the iterator tuple.
void decrement() void decrement()
{ {
detail::tuple_impl_specific::tuple_for_each( detail::tuple_impl_specific::tuple_for_each(
m_iterator_tuple, m_iterator_tuple,
detail::decrement_iterator() detail::decrement_iterator()
); );
} }
// Distance is calculated using the first iterator in the tuple. // Distance is calculated using the first iterator in the tuple.
template<typename OtherIteratorTuple> template<typename OtherIteratorTuple>
typename super_t::difference_type distance_to( typename super_t::difference_type distance_to(
const zip_iterator<OtherIteratorTuple>& other const zip_iterator<OtherIteratorTuple>& other
) const ) const
{ {
return boost::tuples::get<0>(other.get_iterator_tuple()) - return boost::tuples::get<0>(other.get_iterator_tuple()) -
boost::tuples::get<0>(this->get_iterator_tuple()); boost::tuples::get<0>(this->get_iterator_tuple());
} }
// Data Members // Data Members
// ============ // ============
// The iterator tuple. // The iterator tuple.
IteratorTuple m_iterator_tuple; IteratorTuple m_iterator_tuple;
}; };
// Make function for zip iterator // Make function for zip iterator
// //
template<typename IteratorTuple> template<typename IteratorTuple>
zip_iterator<IteratorTuple> inline zip_iterator<IteratorTuple>
make_zip_iterator(IteratorTuple t) make_zip_iterator(IteratorTuple t)
{ return zip_iterator<IteratorTuple>(t); } { return zip_iterator<IteratorTuple>(t); }
} } // namespace iterators
using iterators::zip_iterator;
using iterators::make_zip_iterator;
} // namespace boost
#endif #endif

View File

@ -15,6 +15,7 @@
#ifndef BOOST_NO_OPERATORS_IN_NAMESPACE #ifndef BOOST_NO_OPERATORS_IN_NAMESPACE
namespace boost { namespace boost {
namespace iterators {
#endif #endif
// this should use random_access_iterator_helper but I've had // this should use random_access_iterator_helper but I've had
@ -61,13 +62,19 @@ inline int_iterator<IntT>
operator+(IntT n, int_iterator<IntT> t) { t += n; return t; } operator+(IntT n, int_iterator<IntT> t) { t += n; return t; }
#ifndef BOOST_NO_OPERATORS_IN_NAMESPACE #ifndef BOOST_NO_OPERATORS_IN_NAMESPACE
} /* namespace iterators */
using iterators::int_iterator;
} /* namespace boost */ } /* namespace boost */
#endif #endif
#ifdef BOOST_NO_OPERATORS_IN_NAMESPACE #ifdef BOOST_NO_OPERATORS_IN_NAMESPACE
namespace boost { namespace boost {
using ::int_iterator; using ::int_iterator;
} namespace iterators {
using ::int_iterator;
}}
#endif #endif

View File

@ -29,11 +29,11 @@
namespace boost { namespace boost {
// use this for the value type // use this for the value type
struct dummyT { struct dummyT {
dummyT() { } dummyT() { }
dummyT(detail::dummy_constructor) { } dummyT(detail::dummy_constructor) { }
dummyT(int x) : m_x(x) { } dummyT(int x) : m_x(x) { }
int foo() const { return m_x; } int foo() const { return m_x; }
bool operator==(const dummyT& d) const { return m_x == d.m_x; } bool operator==(const dummyT& d) const { return m_x == d.m_x; }
int m_x; int m_x;
}; };
@ -41,9 +41,10 @@ struct dummyT {
} }
namespace boost { namespace boost {
namespace iterators {
// Tests whether type Iterator satisfies the requirements for a // Tests whether type Iterator satisfies the requirements for a
// TrivialIterator. // TrivialIterator.
// Preconditions: i != j, *i == val // Preconditions: i != j, *i == val
template <class Iterator, class T> template <class Iterator, class T>
void trivial_iterator_test(const Iterator i, const Iterator j, T val) void trivial_iterator_test(const Iterator i, const Iterator j, T val)
@ -84,7 +85,7 @@ void mutable_trivial_iterator_test(const Iterator i, const Iterator j, T val)
// Preconditions: *i == v1, *++i == v2 // Preconditions: *i == v1, *++i == v2
template <class Iterator, class T> template <class Iterator, class T>
void input_iterator_test(Iterator i, T v1, T v2) void input_iterator_test(Iterator i, T v1, T v2)
{ {
Iterator i1(i); Iterator i1(i);
@ -150,7 +151,7 @@ template <> struct lvalue_test<true> {
#endif #endif
template <class Iterator, class T> template <class Iterator, class T>
void forward_iterator_test(Iterator i, T v1, T v2) void forward_iterator_test(Iterator i, T v1, T v2)
{ {
input_iterator_test(i, v1, v2); input_iterator_test(i, v1, v2);
@ -215,7 +216,7 @@ void random_access_iterator_test(Iterator i, int N, TrueVals vals)
int c; int c;
typedef typename boost::detail::iterator_traits<Iterator>::value_type value_type; typedef typename boost::detail::iterator_traits<Iterator>::value_type value_type;
for (c = 0; c < N-1; ++c) { for (c = 0; c < N-1; ++c) {
assert(i == j + c); assert(i == j + c);
assert(*i == vals[c]); assert(*i == vals[c]);
@ -234,7 +235,7 @@ void random_access_iterator_test(Iterator i, int N, TrueVals vals)
assert(i == k - c); assert(i == k - c);
assert(*i == vals[N - 1 - c]); assert(*i == vals[N - 1 - c]);
assert(*i == boost::implicit_cast<value_type>(j[N - 1 - c])); assert(*i == boost::implicit_cast<value_type>(j[N - 1 - c]));
Iterator q = k - c; Iterator q = k - c;
assert(*i == *q); assert(*i == *q);
assert(i > j); assert(i > j);
assert(i >= j); assert(i >= j);
@ -260,6 +261,18 @@ void const_nonconst_iterator_test(Iterator i, ConstIterator j)
assert(i == k); assert(i == k);
} }
} // namespace iterators
using iterators::undefined;
using iterators::trivial_iterator_test;
using iterators::mutable_trivial_iterator_test;
using iterators::input_iterator_test;
using iterators::lvalue_test;
using iterators::forward_iterator_test;
using iterators::bidirectional_iterator_test;
using iterators::random_access_iterator_test;
using iterators::const_nonconst_iterator_test;
} // namespace boost } // namespace boost
#endif // BOOST_ITERATOR_TESTS_HPP #endif // BOOST_ITERATOR_TESTS_HPP

16
include/boost/pointee.hpp Executable file → Normal file
View File

@ -20,7 +20,7 @@
# include <boost/mpl/if.hpp> # include <boost/mpl/if.hpp>
# include <boost/mpl/eval_if.hpp> # include <boost/mpl/eval_if.hpp>
namespace boost { namespace boost {
namespace detail namespace detail
{ {
@ -34,25 +34,25 @@ namespace detail
struct iterator_pointee struct iterator_pointee
{ {
typedef typename iterator_traits<Iterator>::value_type value_type; typedef typename iterator_traits<Iterator>::value_type value_type;
struct impl struct impl
{ {
template <class T> template <class T>
static char test(T const&); static char test(T const&);
static char (& test(value_type&) )[2]; static char (& test(value_type&) )[2];
static Iterator& x; static Iterator& x;
}; };
BOOST_STATIC_CONSTANT(bool, is_constant = sizeof(impl::test(*impl::x)) == 1); BOOST_STATIC_CONSTANT(bool, is_constant = sizeof(impl::test(*impl::x)) == 1);
typedef typename mpl::if_c< typedef typename mpl::if_c<
# if BOOST_WORKAROUND(__BORLANDC__, BOOST_TESTED_AT(0x551)) # if BOOST_WORKAROUND(__BORLANDC__, BOOST_TESTED_AT(0x551))
::boost::detail::iterator_pointee<Iterator>::is_constant ::boost::detail::iterator_pointee<Iterator>::is_constant
# else # else
is_constant is_constant
# endif # endif
, typename add_const<value_type>::type , typename add_const<value_type>::type
, value_type , value_type
>::type type; >::type type;
@ -68,7 +68,7 @@ struct pointee
> >
{ {
}; };
} // namespace boost } // namespace boost
#endif // POINTEE_DWA200415_HPP #endif // POINTEE_DWA200415_HPP

View File

@ -13,6 +13,7 @@
#include <utility> #include <utility>
namespace boost { namespace boost {
namespace iterators {
template <typename Container> template <typename Container>
class shared_container_iterator : public iterator_adaptor< class shared_container_iterator : public iterator_adaptor<
@ -37,7 +38,7 @@ public:
}; };
template <typename Container> template <typename Container>
shared_container_iterator<Container> inline shared_container_iterator<Container>
make_shared_container_iterator(typename Container::iterator iter, make_shared_container_iterator(typename Container::iterator iter,
boost::shared_ptr<Container> const& container) { boost::shared_ptr<Container> const& container) {
typedef shared_container_iterator<Container> iterator; typedef shared_container_iterator<Container> iterator;
@ -47,7 +48,7 @@ make_shared_container_iterator(typename Container::iterator iter,
template <typename Container> template <typename Container>
std::pair< inline std::pair<
shared_container_iterator<Container>, shared_container_iterator<Container>,
shared_container_iterator<Container> > shared_container_iterator<Container> >
make_shared_container_range(boost::shared_ptr<Container> const& container) { make_shared_container_range(boost::shared_ptr<Container> const& container) {
@ -57,6 +58,12 @@ make_shared_container_range(boost::shared_ptr<Container> const& container) {
make_shared_container_iterator(container->end(),container)); make_shared_container_iterator(container->end(),container));
} }
} // namespace iterators
using iterators::shared_container_iterator;
using iterators::make_shared_container_iterator;
using iterators::make_shared_container_range;
} // namespace boost } // namespace boost
#endif // SHARED_CONTAINER_ITERATOR_RG08102002_HPP #endif // SHARED_CONTAINER_ITERATOR_RG08102002_HPP

0
index.html Executable file → Normal file
View File

18
meta/libraries.json Normal file
View File

@ -0,0 +1,18 @@
{
"key": "iterator",
"name": "Iterator",
"authors": [
"Dave Abrahams",
"Jeremy Siek",
"Thomas Witt"
],
"description": "The Boost Iterator Library contains two parts. The first is a system of concepts which extend the C++ standard iterator requirements. The second is a framework of components for building iterators based on these extended concepts and includes several useful iterator adaptors.",
"category": [
"Iterators"
],
"maintainers": [
"David Abrahams <dave -at- boost-consulting.com>",
"Thomas Witt <witt - at - acm.org>",
"Jeffrey Lee Hellrung Jr. <jeffrey.hellrung -at- gmail.com>"
]
}

View File

@ -3,28 +3,28 @@
# file LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt) # file LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt)
test-suite iterator test-suite iterator
: :
# These first two tests will run last, and are expected to fail # These first two tests will run last, and are expected to fail
# for many less-capable compilers. # for many less-capable compilers.
[ compile-fail interoperable_fail.cpp ] [ compile-fail interoperable_fail.cpp ]
# test uses expected success, so that we catch unrelated # test uses expected success, so that we catch unrelated
# compilation problems. # compilation problems.
[ run is_convertible_fail.cpp ] [ run is_convertible_fail.cpp ]
[ run zip_iterator_test.cpp [ run zip_iterator_test.cpp
: : : : : :
# stlport's debug mode generates long symbols which overwhelm # stlport's debug mode generates long symbols which overwhelm
# vc6 # vc6
#<msvc-stlport><*><runtime-build>release #<msvc-stlport><*><runtime-build>release
] ]
# These tests should work for just about everything. # These tests should work for just about everything.
[ compile is_lvalue_iterator.cpp ] [ compile is_lvalue_iterator.cpp ]
[ compile is_readable_iterator.cpp ] [ compile is_readable_iterator.cpp ]
[ compile pointee.cpp ] [ compile pointee.cpp ]
[ run unit_tests.cpp ] [ run unit_tests.cpp ]
[ run concept_tests.cpp ] [ run concept_tests.cpp ]
[ run iterator_adaptor_cc.cpp ] [ run iterator_adaptor_cc.cpp ]
@ -41,8 +41,12 @@ test-suite iterator
[ run counting_iterator_test.cpp ] [ run counting_iterator_test.cpp ]
[ run interoperable.cpp ] [ run interoperable.cpp ]
[ run iterator_traits_test.cpp ] [ run iterator_traits_test.cpp ]
[ run permutation_iterator_test.cpp : : : # <stlport-iostream>on [ run permutation_iterator_test.cpp : : : # <stlport-iostream>on
] ]
[ run function_input_iterator_test.cpp ] [ run function_input_iterator_test.cpp ]
[ run generator_iterator_test.cpp ]
[ run minimum_category.cpp ]
[ compile-fail minimum_category_compile_fail.cpp ]
; ;

0
test/constant_iter_arrow.cpp Executable file → Normal file
View File

0
test/constant_iter_arrow_fail.cpp Executable file → Normal file
View File

0
test/interoperable.cpp Executable file → Normal file
View File

0
test/iter_archetype_default_ctor.cpp Executable file → Normal file
View File

22
test/minimum_category.cpp Normal file
View File

@ -0,0 +1,22 @@
// Copyright Andrey Semashev 2014.
//
// Use, modification and distribution is subject to
// 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)
#include <boost/iterator/minimum_category.hpp>
#include <boost/core/lightweight_test_trait.hpp>
#include <boost/type_traits/is_same.hpp>
#include <iterator>
using boost::is_same;
using boost::iterators::minimum_category;
int main(int, char*[])
{
BOOST_TEST_TRAIT_TRUE((is_same<minimum_category<std::forward_iterator_tag, std::random_access_iterator_tag>::type, std::forward_iterator_tag>));
BOOST_TEST_TRAIT_TRUE((is_same<minimum_category<std::random_access_iterator_tag, std::forward_iterator_tag>::type, std::forward_iterator_tag>));
BOOST_TEST_TRAIT_TRUE((is_same<minimum_category<std::random_access_iterator_tag, std::random_access_iterator_tag>::type, std::random_access_iterator_tag>));
return boost::report_errors();
}

View File

@ -0,0 +1,19 @@
// Copyright Andrey Semashev 2014.
//
// Use, modification and distribution is subject to
// 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)
#include <boost/iterator/minimum_category.hpp>
using boost::iterators::minimum_category;
struct A {};
struct B {};
int main(int, char*[])
{
minimum_category<A, B>::type cat;
return 0;
}

View File

@ -7,7 +7,7 @@
#include "static_assert_same.hpp" #include "static_assert_same.hpp"
#include <boost/iterator/detail/minimum_category.hpp> #include <boost/iterator/minimum_category.hpp>
struct X { int a; }; struct X { int a; };
@ -29,30 +29,30 @@ void operator_arrow_test()
template <class T, class U, class Min> template <class T, class U, class Min>
struct static_assert_min_cat struct static_assert_min_cat
: static_assert_same< : static_assert_same<
typename boost::detail::minimum_category<T,U>::type, Min typename boost::iterators::minimum_category<T,U>::type, Min
> >
{}; {};
void category_test() void category_test()
{ {
using namespace boost; using namespace boost::iterators;
using namespace boost::detail; using namespace boost::iterators::detail;
BOOST_STATIC_ASSERT(( BOOST_STATIC_ASSERT((
!boost::is_convertible< !boost::is_convertible<
std::input_iterator_tag std::input_iterator_tag
, input_output_iterator_tag>::value)); , input_output_iterator_tag>::value));
BOOST_STATIC_ASSERT(( BOOST_STATIC_ASSERT((
!boost::is_convertible< !boost::is_convertible<
std::output_iterator_tag std::output_iterator_tag
, input_output_iterator_tag>::value)); , input_output_iterator_tag>::value));
BOOST_STATIC_ASSERT(( BOOST_STATIC_ASSERT((
boost::is_convertible< boost::is_convertible<
input_output_iterator_tag input_output_iterator_tag
, std::input_iterator_tag>::value)); , std::input_iterator_tag>::value));
BOOST_STATIC_ASSERT(( BOOST_STATIC_ASSERT((
boost::is_convertible< boost::is_convertible<
input_output_iterator_tag input_output_iterator_tag
@ -64,7 +64,7 @@ void category_test()
boost::is_convertible< boost::is_convertible<
std::forward_iterator_tag std::forward_iterator_tag
, input_output_iterator_tag>::value)); , input_output_iterator_tag>::value));
#endif #endif
int test = static_assert_min_cat< int test = static_assert_min_cat<
std::input_iterator_tag,input_output_iterator_tag, std::input_iterator_tag std::input_iterator_tag,input_output_iterator_tag, std::input_iterator_tag
@ -78,7 +78,7 @@ void category_test()
test = static_assert_min_cat< test = static_assert_min_cat<
input_output_iterator_tag,std::forward_iterator_tag, input_output_iterator_tag input_output_iterator_tag,std::forward_iterator_tag, input_output_iterator_tag
>::value; >::value;
#endif #endif
test = static_assert_min_cat< test = static_assert_min_cat<
std::input_iterator_tag,std::forward_iterator_tag, std::input_iterator_tag std::input_iterator_tag,std::forward_iterator_tag, std::input_iterator_tag
@ -93,8 +93,8 @@ void category_test()
test = static_assert_min_cat< test = static_assert_min_cat<
std::output_iterator_tag,std::random_access_iterator_tag, std::output_iterator_tag std::output_iterator_tag,std::random_access_iterator_tag, std::output_iterator_tag
>::value; >::value;
#endif #endif
(void)test; (void)test;
} }

Some files were not shown because too many files have changed in this diff Show More