Finished iterator_adaptor tutorial

Added example test code
Rolled forward old counting_iterator abstract for boost docs.


[SVN r21649]
This commit is contained in:
Dave Abrahams 2004-01-12 20:58:22 +00:00
parent 19dbb5304c
commit 3bf52ec2f2
13 changed files with 488 additions and 138 deletions

View File

@ -3,7 +3,7 @@
<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.2.8: http://docutils.sourceforge.net/" /> <meta name="generator" content="Docutils 0.3.1: http://docutils.sourceforge.net/" />
<title>Counting Iterator</title> <title>Counting Iterator</title>
<meta name="author" content="David Abrahams, Jeremy Siek, Thomas Witt" /> <meta name="author" content="David Abrahams, Jeremy Siek, Thomas Witt" />
<meta name="organization" content="Boost Consulting, Indiana University Open Systems Lab, University of Hanover Institute for Transport Railway Operation and Construction" /> <meta name="organization" content="Boost Consulting, Indiana University Open Systems Lab, University of Hanover Institute for Transport Railway Operation and Construction" />
@ -36,12 +36,21 @@ Railway Operation and Construction</a></td></tr>
<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"></td> <tr class="field"><th class="field-name">abstract:</th><td class="field-body">How would you fill up a vector with the numbers zero
through one hundred using <tt class="literal"><span class="pre">std::copy()</span></tt>? The only iterator
operation missing from builtin integer types is an
<tt class="literal"><span class="pre">operator*()</span></tt> that returns the current value of the integer.
The counting iterator adaptor adds this crucial piece of
functionality to whatever type it wraps. One can use the
counting iterator adaptor not only with integer types, but with
any type that is <strong>Incrementable</strong> (see type requirements
below).</td>
</tr> </tr>
</tbody> </tbody>
</table> </table>
<p><tt class="literal"><span class="pre">counting_iterator</span></tt> adapts an arithmetic type, such as <tt class="literal"><span class="pre">int</span></tt>, by <p><tt class="literal"><span class="pre">counting_iterator</span></tt> adapts an incrementable type such as <tt class="literal"><span class="pre">int</span></tt>
adding an <tt class="literal"><span class="pre">operator*</span></tt> that returns the current value of the object.</p> or <tt class="literal"><span class="pre">std::list&lt;std::string&gt;::iterator</span></tt>, by adding an <tt class="literal"><span class="pre">operator*</span></tt>
that returns the current value of the object.</p>
<div class="contents topic" id="table-of-contents"> <div class="contents topic" id="table-of-contents">
<p class="topic-title"><a name="table-of-contents">Table of Contents</a></p> <p class="topic-title"><a name="table-of-contents">Table of Contents</a></p>
<ul class="simple"> <ul class="simple">
@ -245,10 +254,10 @@ indirectly printing out the numbers from 0 to 7
<p>The source code for this example can be found <a class="reference" href="../example/counting_iterator_example.cpp">here</a>.</p> <p>The source code for this example can be found <a class="reference" href="../example/counting_iterator_example.cpp">here</a>.</p>
</div> </div>
</div> </div>
<hr class="footer"/> <hr class="footer" />
<div class="footer"> <div class="footer">
<a class="reference" href="counting_iterator.rst">View document source</a>. <a class="reference" href="counting_iterator.rst">View document source</a>.
Generated on: 2004-01-12 19:01 UTC. Generated on: 2004-01-12 20:46 UTC.
Generated by <a class="reference" href="http://docutils.sourceforge.net/">Docutils</a> from <a class="reference" href="http://docutils.sourceforge.net/rst.html">reStructuredText</a> source. Generated by <a class="reference" href="http://docutils.sourceforge.net/">Docutils</a> from <a class="reference" href="http://docutils.sourceforge.net/rst.html">reStructuredText</a> source.
</div> </div>
</body> </body>

View File

@ -14,7 +14,15 @@
.. _`Open Systems Lab`: http://www.osl.iu.edu .. _`Open Systems Lab`: http://www.osl.iu.edu
.. _`Institute for Transport Railway Operation and Construction`: http://www.ive.uni-hannover.de .. _`Institute for Transport Railway Operation and Construction`: http://www.ive.uni-hannover.de
:abstract: :abstract: How would you fill up a vector with the numbers zero
through one hundred using ``std::copy()``? The only iterator
operation missing from builtin integer types is an
``operator*()`` that returns the current value of the integer.
The counting iterator adaptor adds this crucial piece of
functionality to whatever type it wraps. One can use the
counting iterator adaptor not only with integer types, but with
any type that is **Incrementable** (see type requirements
below).
.. include:: counting_iterator_abstract.rst .. include:: counting_iterator_abstract.rst

View File

@ -1,2 +1,3 @@
``counting_iterator`` adapts an arithmetic type, such as ``int``, by ``counting_iterator`` adapts an incrementable type such as ``int``
adding an ``operator*`` that returns the current value of the object. or ``std::list<std::string>::iterator``, by adding an ``operator*``
that returns the current value of the object.

View File

@ -3,7 +3,7 @@
<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.2.8: http://docutils.sourceforge.net/" /> <meta name="generator" content="Docutils 0.3.1: http://docutils.sourceforge.net/" />
<title>Iterator Facade and Adaptor</title> <title>Iterator Facade and Adaptor</title>
<meta name="author" content="David Abrahams, Jeremy Siek, Thomas Witt" /> <meta name="author" content="David Abrahams, Jeremy Siek, Thomas Witt" />
<meta name="organization" content="Boost Consulting, Indiana University Open Systems Lab, University of Hanover Institute for Transport Railway Operation and Construction" /> <meta name="organization" content="Boost Consulting, Indiana University Open Systems Lab, University of Hanover Institute for Transport Railway Operation and Construction" />
@ -326,7 +326,7 @@ of the derived iterator type. These member functions are described
briefly below and in more detail in the iterator facade briefly below and in more detail in the iterator facade
requirements.</p> requirements.</p>
<blockquote> <blockquote>
<table class="table" frame="border" rules="all"> <table border class="table">
<colgroup> <colgroup>
<col width="44%" /> <col width="44%" />
<col width="56%" /> <col width="56%" />
@ -725,7 +725,7 @@ is a constant object of a random access traversal iterator type
interoperable with <tt class="literal"><span class="pre">X</span></tt>.</p> interoperable with <tt class="literal"><span class="pre">X</span></tt>.</p>
<a class="target" id="core-operations" name="core-operations"></a><div class="topic"> <a class="target" id="core-operations" name="core-operations"></a><div class="topic">
<p class="topic-title"><tt class="literal"><span class="pre">iterator_facade</span></tt> Core Operations</p> <p class="topic-title"><tt class="literal"><span class="pre">iterator_facade</span></tt> Core Operations</p>
<table class="table" frame="border" rules="all"> <table border class="table">
<colgroup> <colgroup>
<col width="19%" /> <col width="19%" />
<col width="21%" /> <col width="21%" />
@ -1500,7 +1500,7 @@ Iterator and Readable Iterator.</p>
<p>The concepts that <tt class="literal"><span class="pre">reverse_iterator</span></tt> models are dependent on what <p>The concepts that <tt class="literal"><span class="pre">reverse_iterator</span></tt> models are dependent on what
concepts the <tt class="literal"><span class="pre">Iterator</span></tt> argument models, as specified in the concepts the <tt class="literal"><span class="pre">Iterator</span></tt> argument models, as specified in the
following tables.</p> following tables.</p>
<table class="table" frame="border" rules="all"> <table border class="table">
<colgroup> <colgroup>
<col width="48%" /> <col width="48%" />
<col width="52%" /> <col width="52%" />
@ -1519,7 +1519,7 @@ following tables.</p>
</tr> </tr>
</tbody> </tbody>
</table> </table>
<table class="table" frame="border" rules="all"> <table border class="table">
<colgroup> <colgroup>
<col width="41%" /> <col width="41%" />
<col width="59%" /> <col width="59%" />
@ -1541,7 +1541,7 @@ following tables.</p>
</tr> </tr>
</tbody> </tbody>
</table> </table>
<table class="table" frame="border" rules="all"> <table border class="table">
<colgroup> <colgroup>
<col width="62%" /> <col width="62%" />
<col width="38%" /> <col width="38%" />
@ -1734,7 +1734,7 @@ concept that is modeled by the <tt class="literal"><span class="pre">Iterator</s
<p>If <tt class="literal"><span class="pre">transform_iterator</span></tt> is a model of Readable Lvalue Iterator then <p>If <tt class="literal"><span class="pre">transform_iterator</span></tt> is a model of Readable Lvalue Iterator then
it models the following original iterator concepts depending on what it models the following original iterator concepts depending on what
the <tt class="literal"><span class="pre">Iterator</span></tt> argument models.</p> the <tt class="literal"><span class="pre">Iterator</span></tt> argument models.</p>
<table class="table" frame="border" rules="all"> <table border class="table">
<colgroup> <colgroup>
<col width="51%" /> <col width="51%" />
<col width="49%" /> <col width="49%" />
@ -1919,7 +1919,7 @@ Input Iterator.</p>
<p>The concepts that <tt class="literal"><span class="pre">filter_iterator</span></tt> models are dependent on what <p>The concepts that <tt class="literal"><span class="pre">filter_iterator</span></tt> models are dependent on what
concepts the <tt class="literal"><span class="pre">Iterator</span></tt> argument models, as specified in the concepts the <tt class="literal"><span class="pre">Iterator</span></tt> argument models, as specified in the
following tables.</p> following tables.</p>
<table class="table" frame="border" rules="all"> <table border class="table">
<colgroup> <colgroup>
<col width="33%" /> <col width="33%" />
<col width="67%" /> <col width="67%" />
@ -1938,7 +1938,7 @@ following tables.</p>
</tr> </tr>
</tbody> </tbody>
</table> </table>
<table class="table" frame="border" rules="all"> <table border class="table">
<colgroup> <colgroup>
<col width="41%" /> <col width="41%" />
<col width="59%" /> <col width="59%" />
@ -1960,7 +1960,7 @@ following tables.</p>
</tr> </tr>
</tbody> </tbody>
</table> </table>
<table class="table" frame="border" rules="all"> <table border class="table">
<colgroup> <colgroup>
<col width="63%" /> <col width="63%" />
<col width="38%" /> <col width="38%" />
@ -2095,8 +2095,9 @@ or <tt class="literal"><span class="pre">m_pred(*m_iter)</span> <span class="pre
</div> </div>
<div class="section" id="counting-iterator"> <div class="section" id="counting-iterator">
<h3><a class="toc-backref" href="#id61" name="counting-iterator">Counting iterator</a></h3> <h3><a class="toc-backref" href="#id61" name="counting-iterator">Counting iterator</a></h3>
<p><tt class="literal"><span class="pre">counting_iterator</span></tt> adapts an arithmetic type, such as <tt class="literal"><span class="pre">int</span></tt>, by <p><tt class="literal"><span class="pre">counting_iterator</span></tt> adapts an incrementable type such as <tt class="literal"><span class="pre">int</span></tt>
adding an <tt class="literal"><span class="pre">operator*</span></tt> that returns the current value of the object.</p> or <tt class="literal"><span class="pre">std::list&lt;std::string&gt;::iterator</span></tt>, by adding an <tt class="literal"><span class="pre">operator*</span></tt>
that returns the current value of the object.</p>
<div class="section" id="class-template-counting-iterator"> <div class="section" id="class-template-counting-iterator">
<h4><a class="toc-backref" href="#id62" name="class-template-counting-iterator">Class template <tt class="literal"><span class="pre">counting_iterator</span></tt></a></h4> <h4><a class="toc-backref" href="#id62" name="class-template-counting-iterator">Class template <tt class="literal"><span class="pre">counting_iterator</span></tt></a></h4>
<pre class="literal-block"> <pre class="literal-block">
@ -2337,10 +2338,10 @@ LocalWords: OtherIncrementable Coplien -->
</div> </div>
</div> </div>
</div> </div>
<hr class="footer"/> <hr class="footer" />
<div class="footer"> <div class="footer">
<a class="reference" href="facade-and-adaptor.rst">View document source</a>. <a class="reference" href="facade-and-adaptor.rst">View document source</a>.
Generated on: 2004-01-12 20:23 UTC. Generated on: 2004-01-12 20:48 UTC.
Generated by <a class="reference" href="http://docutils.sourceforge.net/">Docutils</a> from <a class="reference" href="http://docutils.sourceforge.net/rst.html">reStructuredText</a> source. Generated by <a class="reference" href="http://docutils.sourceforge.net/">Docutils</a> from <a class="reference" href="http://docutils.sourceforge.net/rst.html">reStructuredText</a> source.
</div> </div>
</body> </body>

View File

@ -3,7 +3,7 @@
<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.2.8: http://docutils.sourceforge.net/" /> <meta name="generator" content="Docutils 0.3.1: http://docutils.sourceforge.net/" />
<title>Iterator Adaptor</title> <title>Iterator Adaptor</title>
<meta name="author" content="David Abrahams, Jeremy Siek, Thomas Witt" /> <meta name="author" content="David Abrahams, Jeremy Siek, Thomas Witt" />
<meta name="organization" content="Boost Consulting, Indiana University Open Systems Lab, University of Hanover Institute for Transport Railway Operation and Construction" /> <meta name="organization" content="Boost Consulting, Indiana University Open Systems Lab, University of Hanover Institute for Transport Railway Operation and Construction" />
@ -57,20 +57,21 @@ core interface functions of <tt class="literal"><span class="pre">iterator_facad
<div class="contents topic" id="table-of-contents"> <div class="contents topic" id="table-of-contents">
<p class="topic-title"><a name="table-of-contents">Table of Contents</a></p> <p class="topic-title"><a name="table-of-contents">Table of Contents</a></p>
<ul class="simple"> <ul class="simple">
<li><a class="reference" href="#introduction" id="id3" name="id3">Introduction</a></li> <li><a class="reference" href="#overview" id="id6" name="id6">Overview</a></li>
<li><a class="reference" href="#reference" id="id4" name="id4">Reference</a><ul> <li><a class="reference" href="#reference" id="id7" name="id7">Reference</a><ul>
<li><a class="reference" href="#iterator-adaptor-requirements" id="id5" name="id5"><tt class="literal"><span class="pre">iterator_adaptor</span></tt> requirements</a></li> <li><a class="reference" href="#iterator-adaptor-requirements" id="id8" name="id8"><tt class="literal"><span class="pre">iterator_adaptor</span></tt> requirements</a></li>
<li><a class="reference" href="#iterator-adaptor-base-class-parameters" id="id6" name="id6"><tt class="literal"><span class="pre">iterator_adaptor</span></tt> base class parameters</a></li> <li><a class="reference" href="#iterator-adaptor-base-class-parameters" id="id9" name="id9"><tt class="literal"><span class="pre">iterator_adaptor</span></tt> base class parameters</a></li>
<li><a class="reference" href="#iterator-adaptor-models" id="id7" name="id7"><tt class="literal"><span class="pre">iterator_adaptor</span></tt> models</a></li> <li><a class="reference" href="#iterator-adaptor-models" id="id10" name="id10"><tt class="literal"><span class="pre">iterator_adaptor</span></tt> models</a></li>
<li><a class="reference" href="#iterator-adaptor-public-operations" id="id8" name="id8"><tt class="literal"><span class="pre">iterator_adaptor</span></tt> public operations</a></li> <li><a class="reference" href="#iterator-adaptor-public-operations" id="id11" name="id11"><tt class="literal"><span class="pre">iterator_adaptor</span></tt> public operations</a></li>
<li><a class="reference" href="#iterator-adaptor-protected-member-functions" id="id9" name="id9"><tt class="literal"><span class="pre">iterator_adaptor</span></tt> protected member functions</a></li> <li><a class="reference" href="#iterator-adaptor-protected-member-functions" id="id12" name="id12"><tt class="literal"><span class="pre">iterator_adaptor</span></tt> protected member functions</a></li>
<li><a class="reference" href="#iterator-adaptor-private-member-functions" id="id10" name="id10"><tt class="literal"><span class="pre">iterator_adaptor</span></tt> private member functions</a></li> <li><a class="reference" href="#iterator-adaptor-private-member-functions" id="id13" name="id13"><tt class="literal"><span class="pre">iterator_adaptor</span></tt> private member functions</a></li>
</ul> </ul>
</li> </li>
<li><a class="reference" href="#tutorial-example" id="id14" name="id14">Tutorial Example</a></li>
</ul> </ul>
</div> </div>
<div class="section" id="introduction"> <div class="section" id="overview">
<h1><a class="toc-backref" href="#id3" name="introduction">Introduction</a></h1> <h1><a class="toc-backref" href="#id6" name="overview">Overview</a></h1>
<!-- Version 1.2 of this ReStructuredText document corresponds to <!-- Version 1.2 of this ReStructuredText document corresponds to
n1530_, the paper accepted by the LWG for TR1. --> n1530_, the paper accepted by the LWG for TR1. -->
<!-- Copyright David Abrahams, Jeremy Siek, and Thomas Witt 2003. All <!-- Copyright David Abrahams, Jeremy Siek, and Thomas Witt 2003. All
@ -84,7 +85,7 @@ instance of the <tt class="literal"><span class="pre">Base</span></tt> type, whi
<table class="footnote" frame="void" id="base" rules="none"> <table class="footnote" frame="void" id="base" rules="none">
<colgroup><col class="label" /><col /></colgroup> <colgroup><col class="label" /><col /></colgroup>
<tbody valign="top"> <tbody valign="top">
<tr><td class="label"><a class="fn-backref" href="#id1" name="base">[1]</a></td><td>The term &quot;Base&quot; here does not refer to a base class and is <tr><td class="label"><a name="base">[1]</a></td><td><em>(<a class="fn-backref" href="#id1">1</a>, <a class="fn-backref" href="#id3">2</a>)</em> The term &quot;Base&quot; here does not refer to a base class and is
not meant to imply the use of derivation. We have followed the lead not meant to imply the use of derivation. We have followed the lead
of the standard library, which provides a base() function to access of the standard library, which provides a base() function to access
the underlying iterator object of a <tt class="literal"><span class="pre">reverse_iterator</span></tt> adaptor.</td></tr> the underlying iterator object of a <tt class="literal"><span class="pre">reverse_iterator</span></tt> adaptor.</td></tr>
@ -111,7 +112,7 @@ template parameter may not always be identical to the iterator's
that assumption.</p> that assumption.</p>
</div> </div>
<div class="section" id="reference"> <div class="section" id="reference">
<h1><a class="toc-backref" href="#id4" name="reference">Reference</a></h1> <h1><a class="toc-backref" href="#id7" name="reference">Reference</a></h1>
<!-- Version 1.4 of this ReStructuredText document corresponds to <!-- Version 1.4 of this ReStructuredText document corresponds to
n1530_, the paper accepted by the LWG for TR1. --> n1530_, the paper accepted by the LWG for TR1. -->
<!-- Copyright David Abrahams, Jeremy Siek, and Thomas Witt 2003. All <!-- Copyright David Abrahams, Jeremy Siek, and Thomas Witt 2003. All
@ -159,13 +160,13 @@ class iterator_adaptor
}; };
</pre> </pre>
<a class="target" id="requirements" name="requirements"></a><div class="section" id="iterator-adaptor-requirements"> <a class="target" id="requirements" name="requirements"></a><div class="section" id="iterator-adaptor-requirements">
<h2><a class="toc-backref" href="#id5" name="iterator-adaptor-requirements"><tt class="literal"><span class="pre">iterator_adaptor</span></tt> requirements</a></h2> <h2><a class="toc-backref" href="#id8" name="iterator-adaptor-requirements"><tt class="literal"><span class="pre">iterator_adaptor</span></tt> requirements</a></h2>
<p>The <tt class="literal"><span class="pre">Derived</span></tt> template argument must be a publicly derived from <p>The <tt class="literal"><span class="pre">Derived</span></tt> template argument must be a publicly derived from
<tt class="literal"><span class="pre">iterator_adaptor</span></tt>.</p> <tt class="literal"><span class="pre">iterator_adaptor</span></tt>.</p>
<p>The <tt class="literal"><span class="pre">Base</span></tt> argument shall be Assignable and Copy Constructible.</p> <p>The <tt class="literal"><span class="pre">Base</span></tt> argument shall be Assignable and Copy Constructible.</p>
<a class="target" id="base-parameters" name="base-parameters"></a></div> <a class="target" id="base-parameters" name="base-parameters"></a></div>
<div class="section" id="iterator-adaptor-base-class-parameters"> <div class="section" id="iterator-adaptor-base-class-parameters">
<h2><a class="toc-backref" href="#id6" name="iterator-adaptor-base-class-parameters"><tt class="literal"><span class="pre">iterator_adaptor</span></tt> base class parameters</a></h2> <h2><a class="toc-backref" href="#id9" name="iterator-adaptor-base-class-parameters"><tt class="literal"><span class="pre">iterator_adaptor</span></tt> base class parameters</a></h2>
<p>The <em>V</em>, <em>C</em>, <em>R</em>, and <em>D</em> parameters of the <tt class="literal"><span class="pre">iterator_facade</span></tt> <p>The <em>V</em>, <em>C</em>, <em>R</em>, and <em>D</em> parameters of the <tt class="literal"><span class="pre">iterator_facade</span></tt>
used as a base class in the summary of <tt class="literal"><span class="pre">iterator_adaptor</span></tt> used as a base class in the summary of <tt class="literal"><span class="pre">iterator_adaptor</span></tt>
above are defined as follows:</p> above are defined as follows:</p>
@ -195,7 +196,7 @@ above are defined as follows:</p>
</pre> </pre>
</div> </div>
<div class="section" id="iterator-adaptor-models"> <div class="section" id="iterator-adaptor-models">
<h2><a class="toc-backref" href="#id7" name="iterator-adaptor-models"><tt class="literal"><span class="pre">iterator_adaptor</span></tt> models</a></h2> <h2><a class="toc-backref" href="#id10" name="iterator-adaptor-models"><tt class="literal"><span class="pre">iterator_adaptor</span></tt> models</a></h2>
<p>In order for <tt class="literal"><span class="pre">Derived</span></tt> to model the iterator concepts corresponding <p>In order for <tt class="literal"><span class="pre">Derived</span></tt> to model the iterator concepts corresponding
to <tt class="literal"><span class="pre">iterator_traits&lt;Derived&gt;::iterator_category</span></tt>, the expressions to <tt class="literal"><span class="pre">iterator_traits&lt;Derived&gt;::iterator_category</span></tt>, the expressions
involving <tt class="literal"><span class="pre">m_iterator</span></tt> in the specifications of those private member involving <tt class="literal"><span class="pre">m_iterator</span></tt> in the specifications of those private member
@ -205,7 +206,7 @@ expression involving <tt class="literal"><span class="pre">Derived</span></tt> i
<!-- The above is confusing and needs a rewrite. -JGS --> <!-- The above is confusing and needs a rewrite. -JGS -->
</div> </div>
<div class="section" id="iterator-adaptor-public-operations"> <div class="section" id="iterator-adaptor-public-operations">
<h2><a class="toc-backref" href="#id8" name="iterator-adaptor-public-operations"><tt class="literal"><span class="pre">iterator_adaptor</span></tt> public operations</a></h2> <h2><a class="toc-backref" href="#id11" name="iterator-adaptor-public-operations"><tt class="literal"><span class="pre">iterator_adaptor</span></tt> public operations</a></h2>
<p><tt class="literal"><span class="pre">iterator_adaptor();</span></tt></p> <p><tt class="literal"><span class="pre">iterator_adaptor();</span></tt></p>
<table class="field-list" frame="void" rules="none"> <table class="field-list" frame="void" rules="none">
<col class="field-name" /> <col class="field-name" />
@ -239,7 +240,7 @@ expression involving <tt class="literal"><span class="pre">Derived</span></tt> i
</table> </table>
</div> </div>
<div class="section" id="iterator-adaptor-protected-member-functions"> <div class="section" id="iterator-adaptor-protected-member-functions">
<h2><a class="toc-backref" href="#id9" name="iterator-adaptor-protected-member-functions"><tt class="literal"><span class="pre">iterator_adaptor</span></tt> protected member functions</a></h2> <h2><a class="toc-backref" href="#id12" name="iterator-adaptor-protected-member-functions"><tt class="literal"><span class="pre">iterator_adaptor</span></tt> protected member functions</a></h2>
<p><tt class="literal"><span class="pre">Base</span> <span class="pre">const&amp;</span> <span class="pre">base_reference()</span> <span class="pre">const;</span></tt></p> <p><tt class="literal"><span class="pre">Base</span> <span class="pre">const&amp;</span> <span class="pre">base_reference()</span> <span class="pre">const;</span></tt></p>
<table class="field-list" frame="void" rules="none"> <table class="field-list" frame="void" rules="none">
<col class="field-name" /> <col class="field-name" />
@ -260,7 +261,7 @@ expression involving <tt class="literal"><span class="pre">Derived</span></tt> i
</table> </table>
</div> </div>
<div class="section" id="iterator-adaptor-private-member-functions"> <div class="section" id="iterator-adaptor-private-member-functions">
<h2><a class="toc-backref" href="#id10" name="iterator-adaptor-private-member-functions"><tt class="literal"><span class="pre">iterator_adaptor</span></tt> private member functions</a></h2> <h2><a class="toc-backref" href="#id13" name="iterator-adaptor-private-member-functions"><tt class="literal"><span class="pre">iterator_adaptor</span></tt> private member functions</a></h2>
<p><tt class="literal"><span class="pre">typename</span> <span class="pre">iterator_adaptor::reference</span> <span class="pre">dereference()</span> <span class="pre">const;</span></tt></p> <p><tt class="literal"><span class="pre">typename</span> <span class="pre">iterator_adaptor::reference</span> <span class="pre">dereference()</span> <span class="pre">const;</span></tt></p>
<table class="field-list" frame="void" rules="none"> <table class="field-list" frame="void" rules="none">
<col class="field-name" /> <col class="field-name" />
@ -328,11 +329,114 @@ typename iterator_adaptor::difference_type distance_to(
</table> </table>
</div> </div>
</div> </div>
<div class="section" id="tutorial-example">
<h1><a class="toc-backref" href="#id14" name="tutorial-example">Tutorial Example</a></h1>
<!-- Copyright David Abrahams 2004. 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) -->
<p>In this section we'll further refine the <tt class="literal"><span class="pre">node_iter</span></tt> class
template we developed in the <a class="reference" href="iterator_facade.html#tutorial-example"><tt class="literal"><span class="pre">iterator_facade</span></tt> tutorial</a>. If you haven't already
read that material, you should go back now and check it out because
we're going to pick up right where it left off.</p>
<div class="sidebar">
<p class="sidebar-title"><tt class="literal"><span class="pre">node_base*</span></tt> really <em>is</em> an iterator</p>
<p>It's not really a very interesting iterator, since <tt class="literal"><span class="pre">node_base</span></tt>
is an abstract class: a pointer to a <tt class="literal"><span class="pre">node_base</span></tt> just points
at some base subobject of an instance of some other class, and
incrementing a <tt class="literal"><span class="pre">node_base*</span></tt> moves it past this base subobject
to who-knows-where? The most we can do with that incremented
position is to compare another <tt class="literal"><span class="pre">node_base*</span></tt> to it. In other
words, the original iterator traverses a one-element array.</p>
</div> </div>
<hr class="footer"/> <p>You probably didn't think of it that way, but the <tt class="literal"><span class="pre">node_base*</span></tt>
object which underlies <tt class="literal"><span class="pre">node_iterator</span></tt> is itself an iterator,
just like all other pointers. If we examine that pointer closely
from an iterator perspective, we can see that it has much in common
with the <tt class="literal"><span class="pre">node_iterator</span></tt> we're building. First, they share most
of the same associated types (<tt class="literal"><span class="pre">value_type</span></tt>, <tt class="literal"><span class="pre">reference</span></tt>,
<tt class="literal"><span class="pre">pointer</span></tt>, and <tt class="literal"><span class="pre">difference_type</span></tt>). Second, even much of the
core functionality is the same: <tt class="literal"><span class="pre">operator*</span></tt> and <tt class="literal"><span class="pre">operator==</span></tt> on
the <tt class="literal"><span class="pre">node_iterator</span></tt> just return the result of invoking the same
operations on the underlying pointer, via the <tt class="literal"><span class="pre">node_iterator</span></tt>'s
<a class="reference" href="iterator_facade.html#implementing-the-core-operations"><tt class="literal"><span class="pre">dereference</span></tt> and <tt class="literal"><span class="pre">equal</span></tt> member functions</a>)</p>
<p>It turns out that the pattern of building an iterator on another
iterator-like type (the <tt class="literal"><span class="pre">Base</span></tt> <a class="footnote-reference" href="#base" id="id3" name="id3"><sup>1</sup></a> type) while modifying
just a few aspects of the underlying type's behavior is an
extremely common one, and it's the pattern addressed by
<tt class="literal"><span class="pre">iterator_adaptor</span></tt>. Using <tt class="literal"><span class="pre">iterator_adaptor</span></tt> is very much like
using <tt class="literal"><span class="pre">iterator_facade</span></tt>, but because iterator_adaptor tries to
mimic as much of the <tt class="literal"><span class="pre">Base</span></tt> type's behavior as possible, we
neither have to supply a <tt class="literal"><span class="pre">Value</span></tt> argument, nor implement any core
behaviors other than <tt class="literal"><span class="pre">increment</span></tt>. The implementation of
<tt class="literal"><span class="pre">node_iter</span></tt> is thus reduced to:</p>
<pre class="literal-block">
template &lt;class Value&gt;
class node_iter
: public boost::iterator_adaptor&lt;
node_iter&lt;Value&gt; // Derived
, Value* // Base
, boost::use_default // Value
, boost::forward_traversal_tag // CategoryOrTraversal
&gt;
{
private:
struct enabler {}; // a private type avoids misuse
typedef boost::iterator_adaptor&lt;
node_iter&lt;Value&gt;, Value*, boost::use_default, boost::forward_traversal_tag
&gt; super_t;
public:
node_iter()
: super_t(0) {}
explicit node_iter(Value* p)
: super_t(p) {}
template &lt;class OtherValue&gt;
node_iter(
node_iter&lt;OtherValue&gt; const&amp; other
, typename boost::enable_if&lt;
boost::is_convertible&lt;OtherValue*,Value*&gt;
, enabler
&gt;::type = enabler()
)
: super_t(other.base()) {}
private:
friend class boost::iterator_core_access;
void increment() { this-&gt;base_reference() = this-&gt;base()-&gt;next(); }
};
</pre>
<p>You can see an example program which exercises this version of the
node iterators <a class="reference" href="../example/node_iterator3.cpp">here</a>.</p>
<p>In the case of <tt class="literal"><span class="pre">node_iter</span></tt>, it's not very compelling to pass
<tt class="literal"><span class="pre">boost::use_default</span></tt> as <tt class="literal"><span class="pre">iterator_adaptor</span></tt>'s <tt class="literal"><span class="pre">Value</span></tt>
argument; we could have just passed <tt class="literal"><span class="pre">node_iter</span></tt>'s <tt class="literal"><span class="pre">Value</span></tt>
along to <tt class="literal"><span class="pre">iterator_adaptor</span></tt>, and that'd even be shorter! Most
iterator class templates built with <tt class="literal"><span class="pre">iterator_adaptor</span></tt> are
parameterized on another iterator type, rather than on its
<tt class="literal"><span class="pre">value_type</span></tt>. For example, <tt class="literal"><span class="pre">boost::reverse_iterator</span></tt> takes an
iterator type argument and reverses its direction of traversal,
since the original iterator and the reversed one have all the same
associated types, <tt class="literal"><span class="pre">iterator_adaptor</span></tt>'s delegation of default
types to its <tt class="literal"><span class="pre">Base</span></tt> saves the implementor of
<tt class="literal"><span class="pre">boost::reverse_iterator</span></tt> from writing</p>
<pre class="literal-block">
std::iterator_traits&lt;Iterator&gt;::<em>some-associated-type</em>
</pre>
<p>at least four times.</p>
<p>We urge you to review the documentation and implementations of
<a class="reference" href="reverse_iterator.html"><tt class="literal"><span class="pre">reverse_iterator</span></tt></a> and the other Boost <a class="reference" href="index.html#specialized-adaptors">specialized iterator
adaptors</a> to get an idea of the sorts of things you can do with
<tt class="literal"><span class="pre">iterator_adaptor</span></tt>. In particular, have a look at
<a class="reference" href="counting_iterator.html"><tt class="literal"><span class="pre">counting_iterator</span></tt></a>, which demonstrates that <tt class="literal"><span class="pre">iterator_adaptor</span></tt>'s <tt class="literal"><span class="pre">Base</span></tt> type needn't be an iterator.</p>
</div>
</div>
<hr class="footer" />
<div class="footer"> <div class="footer">
<a class="reference" href="iterator_adaptor.rst">View document source</a>. <a class="reference" href="iterator_adaptor.rst">View document source</a>.
Generated on: 2004-01-12 18:05 UTC. Generated on: 2004-01-12 20:28 UTC.
Generated by <a class="reference" href="http://docutils.sourceforge.net/">Docutils</a> from <a class="reference" href="http://docutils.sourceforge.net/rst.html">reStructuredText</a> source. Generated by <a class="reference" href="http://docutils.sourceforge.net/">Docutils</a> from <a class="reference" href="http://docutils.sourceforge.net/rst.html">reStructuredText</a> source.
</div> </div>
</body> </body>

View File

@ -20,8 +20,8 @@
.. contents:: Table of Contents .. contents:: Table of Contents
Introduction Overview
============ ========
.. include:: iterator_adaptor_body.rst .. include:: iterator_adaptor_body.rst
@ -30,3 +30,8 @@ Reference
========= =========
.. include:: iterator_adaptor_ref.rst .. include:: iterator_adaptor_ref.rst
Tutorial Example
================
.. include:: iterator_adaptor_tutorial.rst

125
doc/iterator_adaptor_tutorial.rst Executable file
View File

@ -0,0 +1,125 @@
.. Copyright David Abrahams 2004. 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)
In this section we'll further refine the ``node_iter`` class
template we developed in the |fac_tut|_. If you haven't already
read that material, you should go back now and check it out because
we're going to pick up right where it left off.
.. |fac_tut| replace:: ``iterator_facade`` tutorial
.. _fac_tut: iterator_facade.html#tutorial-example
.. sidebar:: ``node_base*`` really *is* an iterator
It's not really a very interesting iterator, since ``node_base``
is an abstract class: a pointer to a ``node_base`` just points
at some base subobject of an instance of some other class, and
incrementing a ``node_base*`` moves it past this base subobject
to who-knows-where? The most we can do with that incremented
position is to compare another ``node_base*`` to it. In other
words, the original iterator traverses a one-element array.
You probably didn't think of it that way, but the ``node_base*``
object which underlies ``node_iterator`` is itself an iterator,
just like all other pointers. If we examine that pointer closely
from an iterator perspective, we can see that it has much in common
with the ``node_iterator`` we're building. First, they share most
of the same associated types (``value_type``, ``reference``,
``pointer``, and ``difference_type``). Second, even much of the
core functionality is the same: ``operator*`` and ``operator==`` on
the ``node_iterator`` just return the result of invoking the same
operations on the underlying pointer, via the ``node_iterator``\ 's
|dereference_and_equal|_)
.. |dereference_and_equal| replace:: ``dereference`` and ``equal`` member functions
.. _dereference_and_equal: iterator_facade.html#implementing-the-core-operations
It turns out that the pattern of building an iterator on another
iterator-like type (the ``Base`` [#base]_ type) while modifying
just a few aspects of the underlying type's behavior is an
extremely common one, and it's the pattern addressed by
``iterator_adaptor``. Using ``iterator_adaptor`` is very much like
using ``iterator_facade``, but because iterator_adaptor tries to
mimic as much of the ``Base`` type's behavior as possible, we
neither have to supply a ``Value`` argument, nor implement any core
behaviors other than ``increment``. The implementation of
``node_iter`` is thus reduced to::
template <class Value>
class node_iter
: public boost::iterator_adaptor<
node_iter<Value> // Derived
, Value* // Base
, boost::use_default // Value
, boost::forward_traversal_tag // CategoryOrTraversal
>
{
private:
struct enabler {}; // a private type avoids misuse
typedef boost::iterator_adaptor<
node_iter<Value>, Value*, boost::use_default, boost::forward_traversal_tag
> super_t;
public:
node_iter()
: super_t(0) {}
explicit node_iter(Value* p)
: super_t(p) {}
template <class OtherValue>
node_iter(
node_iter<OtherValue> const& other
, typename boost::enable_if<
boost::is_convertible<OtherValue*,Value*>
, enabler
>::type = enabler()
)
: super_t(other.base()) {}
private:
friend class boost::iterator_core_access;
void increment() { this->base_reference() = this->base()->next(); }
};
You can see an example program which exercises this version of the
node iterators `here`__.
__ ../example/node_iterator3.cpp
In the case of ``node_iter``, it's not very compelling to pass
``boost::use_default`` as ``iterator_adaptor``\ 's ``Value``
argument; we could have just passed ``node_iter``\ 's ``Value``
along to ``iterator_adaptor``, and that'd even be shorter! Most
iterator class templates built with ``iterator_adaptor`` are
parameterized on another iterator type, rather than on its
``value_type``. For example, ``boost::reverse_iterator`` takes an
iterator type argument and reverses its direction of traversal,
since the original iterator and the reversed one have all the same
associated types, ``iterator_adaptor``\ 's delegation of default
types to its ``Base`` saves the implementor of
``boost::reverse_iterator`` from writing
.. parsed-literal::
std::iterator_traits<Iterator>::*some-associated-type*
at least four times.
We urge you to review the documentation and implementations of
|reverse_iterator|_ and the other Boost `specialized iterator
adaptors`__ to get an idea of the sorts of things you can do with
``iterator_adaptor``. In particular, have a look at
|counting_iterator|_, which demonstrates that ``iterator_adaptor``\
's ``Base`` type needn't be an iterator.
.. |reverse_iterator| replace:: ``reverse_iterator``
.. _reverse_iterator: reverse_iterator.html
.. |counting_iterator| replace:: ``counting_iterator``
.. _counting_iterator: counting_iterator.html
__ index.html#specialized-adaptors

View File

@ -45,44 +45,44 @@ and associated types, to be supplied by a derived iterator class.</td>
<div class="contents topic" id="table-of-contents"> <div class="contents topic" id="table-of-contents">
<p class="topic-title"><a name="table-of-contents">Table of Contents</a></p> <p class="topic-title"><a name="table-of-contents">Table of Contents</a></p>
<ul class="simple"> <ul class="simple">
<li><a class="reference" href="#overview" id="id21" name="id21">Overview</a><ul> <li><a class="reference" href="#overview" id="id20" name="id20">Overview</a><ul>
<li><a class="reference" href="#usage" id="id22" name="id22">Usage</a></li> <li><a class="reference" href="#usage" id="id21" name="id21">Usage</a></li>
<li><a class="reference" href="#iterator-core-access" id="id23" name="id23">Iterator Core Access</a></li> <li><a class="reference" href="#iterator-core-access" id="id22" name="id22">Iterator Core Access</a></li>
<li><a class="reference" href="#operator" id="id24" name="id24"><tt class="literal"><span class="pre">operator[]</span></tt></a></li> <li><a class="reference" href="#operator" id="id23" name="id23"><tt class="literal"><span class="pre">operator[]</span></tt></a></li>
<li><a class="reference" href="#id2" id="id25" name="id25"><tt class="literal"><span class="pre">operator-&gt;</span></tt></a></li> <li><a class="reference" href="#id2" id="id24" name="id24"><tt class="literal"><span class="pre">operator-&gt;</span></tt></a></li>
</ul> </ul>
</li> </li>
<li><a class="reference" href="#reference" id="id26" name="id26">Reference</a><ul> <li><a class="reference" href="#reference" id="id25" name="id25">Reference</a><ul>
<li><a class="reference" href="#iterator-facade-requirements" id="id27" name="id27"><tt class="literal"><span class="pre">iterator_facade</span></tt> Requirements</a></li> <li><a class="reference" href="#iterator-facade-requirements" id="id26" name="id26"><tt class="literal"><span class="pre">iterator_facade</span></tt> Requirements</a></li>
<li><a class="reference" href="#iterator-facade-iterator-category" id="id28" name="id28"><tt class="literal"><span class="pre">iterator_facade</span></tt> iterator category</a></li> <li><a class="reference" href="#iterator-facade-iterator-category" id="id27" name="id27"><tt class="literal"><span class="pre">iterator_facade</span></tt> iterator category</a></li>
<li><a class="reference" href="#iterator-facade-operations" id="id29" name="id29"><tt class="literal"><span class="pre">iterator_facade</span></tt> operations</a></li> <li><a class="reference" href="#iterator-facade-operations" id="id28" name="id28"><tt class="literal"><span class="pre">iterator_facade</span></tt> operations</a></li>
</ul> </ul>
</li> </li>
<li><a class="reference" href="#tutorial-example" id="id30" name="id30">Tutorial Example</a><ul> <li><a class="reference" href="#tutorial-example" id="id29" name="id29">Tutorial Example</a><ul>
<li><a class="reference" href="#the-problem" id="id31" name="id31">The Problem</a></li> <li><a class="reference" href="#the-problem" id="id30" name="id30">The Problem</a></li>
<li><a class="reference" href="#a-basic-iterator-using-iterator-facade" id="id32" name="id32">A Basic Iterator Using <tt class="literal"><span class="pre">iterator_facade</span></tt></a><ul> <li><a class="reference" href="#a-basic-iterator-using-iterator-facade" id="id31" name="id31">A Basic Iterator Using <tt class="literal"><span class="pre">iterator_facade</span></tt></a><ul>
<li><a class="reference" href="#template-arguments-for-iterator-facade" id="id33" name="id33">Template Arguments for <tt class="literal"><span class="pre">iterator_facade</span></tt></a><ul> <li><a class="reference" href="#template-arguments-for-iterator-facade" id="id32" name="id32">Template Arguments for <tt class="literal"><span class="pre">iterator_facade</span></tt></a><ul>
<li><a class="reference" href="#derived" id="id34" name="id34"><tt class="literal"><span class="pre">Derived</span></tt></a></li> <li><a class="reference" href="#derived" id="id33" name="id33"><tt class="literal"><span class="pre">Derived</span></tt></a></li>
<li><a class="reference" href="#value" id="id35" name="id35"><tt class="literal"><span class="pre">Value</span></tt></a></li> <li><a class="reference" href="#value" id="id34" name="id34"><tt class="literal"><span class="pre">Value</span></tt></a></li>
<li><a class="reference" href="#categoryortraversal" id="id36" name="id36"><tt class="literal"><span class="pre">CategoryOrTraversal</span></tt></a></li> <li><a class="reference" href="#categoryortraversal" id="id35" name="id35"><tt class="literal"><span class="pre">CategoryOrTraversal</span></tt></a></li>
<li><a class="reference" href="#id10" id="id37" name="id37"><tt class="literal"><span class="pre">Reference</span></tt></a></li> <li><a class="reference" href="#id10" id="id36" name="id36"><tt class="literal"><span class="pre">Reference</span></tt></a></li>
<li><a class="reference" href="#difference" id="id38" name="id38"><tt class="literal"><span class="pre">Difference</span></tt></a></li> <li><a class="reference" href="#difference" id="id37" name="id37"><tt class="literal"><span class="pre">Difference</span></tt></a></li>
</ul> </ul>
</li> </li>
<li><a class="reference" href="#constructors-and-data-members" id="id39" name="id39">Constructors and Data Members</a></li> <li><a class="reference" href="#constructors-and-data-members" id="id38" name="id38">Constructors and Data Members</a></li>
<li><a class="reference" href="#id12" id="id40" name="id40">Core Operations</a></li> <li><a class="reference" href="#implementing-the-core-operations" id="id39" name="id39">Implementing the Core Operations</a></li>
</ul> </ul>
</li> </li>
<li><a class="reference" href="#a-constant-node-iterator" id="id41" name="id41">A constant <tt class="literal"><span class="pre">node_iterator</span></tt></a></li> <li><a class="reference" href="#a-constant-node-iterator" id="id40" name="id40">A constant <tt class="literal"><span class="pre">node_iterator</span></tt></a></li>
<li><a class="reference" href="#interoperability" id="id42" name="id42">Interoperability</a></li> <li><a class="reference" href="#interoperability" id="id41" name="id41">Interoperability</a></li>
<li><a class="reference" href="#telling-the-truth" id="id43" name="id43">Telling the Truth</a></li> <li><a class="reference" href="#telling-the-truth" id="id42" name="id42">Telling the Truth</a></li>
<li><a class="reference" href="#wrap-up" id="id44" name="id44">Wrap Up</a></li> <li><a class="reference" href="#wrap-up" id="id43" name="id43">Wrap Up</a></li>
</ul> </ul>
</li> </li>
</ul> </ul>
</div> </div>
<div class="section" id="overview"> <div class="section" id="overview">
<h1><a class="toc-backref" href="#id21" name="overview">Overview</a></h1> <h1><a class="toc-backref" href="#id20" name="overview">Overview</a></h1>
<!-- Version 1.1 of this ReStructuredText document corresponds to <!-- Version 1.1 of this ReStructuredText document corresponds to
n1530_, the paper accepted by the LWG for TR1. --> n1530_, the paper accepted by the LWG for TR1. -->
<!-- Copyright David Abrahams, Jeremy Siek, and Thomas Witt 2003. All <!-- Copyright David Abrahams, Jeremy Siek, and Thomas Witt 2003. All
@ -127,7 +127,7 @@ impossible.</li>
</ol> </ol>
</blockquote> </blockquote>
<div class="section" id="usage"> <div class="section" id="usage">
<h2><a class="toc-backref" href="#id22" name="usage">Usage</a></h2> <h2><a class="toc-backref" href="#id21" name="usage">Usage</a></h2>
<p>The user of <tt class="literal"><span class="pre">iterator_facade</span></tt> derives his iterator class from a <p>The user of <tt class="literal"><span class="pre">iterator_facade</span></tt> derives his iterator class from a
specialization of <tt class="literal"><span class="pre">iterator_facade</span></tt> and passes the derived specialization of <tt class="literal"><span class="pre">iterator_facade</span></tt> and passes the derived
iterator class as <tt class="literal"><span class="pre">iterator_facade</span></tt>'s first template parameter. iterator class as <tt class="literal"><span class="pre">iterator_facade</span></tt>'s first template parameter.
@ -191,7 +191,7 @@ Iterator or a more-refined iterator concept, a default constructor is
required.</p> required.</p>
</div> </div>
<div class="section" id="iterator-core-access"> <div class="section" id="iterator-core-access">
<h2><a class="toc-backref" href="#id23" name="iterator-core-access">Iterator Core Access</a></h2> <h2><a class="toc-backref" href="#id22" name="iterator-core-access">Iterator Core Access</a></h2>
<p><tt class="literal"><span class="pre">iterator_facade</span></tt> and the operator implementations need to be able <p><tt class="literal"><span class="pre">iterator_facade</span></tt> and the operator implementations need to be able
to access the core member functions in the derived class. Making the to access the core member functions in the derived class. Making the
core member functions public would expose an implementation detail to core member functions public would expose an implementation detail to
@ -225,7 +225,7 @@ open a safety loophole, as every core member function preserves the
invariants of the iterator.</p> invariants of the iterator.</p>
</div> </div>
<div class="section" id="operator"> <div class="section" id="operator">
<h2><a class="toc-backref" href="#id24" name="operator"><tt class="literal"><span class="pre">operator[]</span></tt></a></h2> <h2><a class="toc-backref" href="#id23" name="operator"><tt class="literal"><span class="pre">operator[]</span></tt></a></h2>
<p>The indexing operator for a generalized iterator presents special <p>The indexing operator for a generalized iterator presents special
challenges. A random access iterator's <tt class="literal"><span class="pre">operator[]</span></tt> is only challenges. A random access iterator's <tt class="literal"><span class="pre">operator[]</span></tt> is only
required to return something convertible to its <tt class="literal"><span class="pre">value_type</span></tt>. required to return something convertible to its <tt class="literal"><span class="pre">value_type</span></tt>.
@ -248,7 +248,7 @@ class; it will hide the one supplied by <tt class="literal"><span class="pre">it
clients of her iterator.</p> clients of her iterator.</p>
<a class="target" id="operator-arrow" name="operator-arrow"></a></div> <a class="target" id="operator-arrow" name="operator-arrow"></a></div>
<div class="section" id="id2"> <div class="section" id="id2">
<h2><a class="toc-backref" href="#id25" name="id2"><tt class="literal"><span class="pre">operator-&gt;</span></tt></a></h2> <h2><a class="toc-backref" href="#id24" name="id2"><tt class="literal"><span class="pre">operator-&gt;</span></tt></a></h2>
<p>The <tt class="literal"><span class="pre">reference</span></tt> type of a readable iterator (and today's input <p>The <tt class="literal"><span class="pre">reference</span></tt> type of a readable iterator (and today's input
iterator) need not in fact be a reference, so long as it is iterator) need not in fact be a reference, so long as it is
convertible to the iterator's <tt class="literal"><span class="pre">value_type</span></tt>. When the <tt class="literal"><span class="pre">value_type</span></tt> convertible to the iterator's <tt class="literal"><span class="pre">value_type</span></tt>. When the <tt class="literal"><span class="pre">value_type</span></tt>
@ -271,7 +271,7 @@ Patterns, C++ Report, February 1995, pp. 24-27.</td></tr>
</div> </div>
</div> </div>
<div class="section" id="reference"> <div class="section" id="reference">
<h1><a class="toc-backref" href="#id26" name="reference">Reference</a></h1> <h1><a class="toc-backref" href="#id25" name="reference">Reference</a></h1>
<!-- Version 1.3 of this ReStructuredText document corresponds to <!-- Version 1.3 of this ReStructuredText document corresponds to
n1530_, the paper accepted by the LWG for TR1. --> n1530_, the paper accepted by the LWG for TR1. -->
<!-- Copyright David Abrahams, Jeremy Siek, and Thomas Witt 2003. All <!-- Copyright David Abrahams, Jeremy Siek, and Thomas Witt 2003. All
@ -383,7 +383,7 @@ struct enable_if_interoperable
{}; {};
</pre> </pre>
<div class="section" id="iterator-facade-requirements"> <div class="section" id="iterator-facade-requirements">
<h2><a class="toc-backref" href="#id27" name="iterator-facade-requirements"><tt class="literal"><span class="pre">iterator_facade</span></tt> Requirements</a></h2> <h2><a class="toc-backref" href="#id26" name="iterator-facade-requirements"><tt class="literal"><span class="pre">iterator_facade</span></tt> Requirements</a></h2>
<p>The following table describes the typical valid expressions on <p>The following table describes the typical valid expressions on
<tt class="literal"><span class="pre">iterator_facade</span></tt>'s <tt class="literal"><span class="pre">Derived</span></tt> parameter, depending on the <tt class="literal"><span class="pre">iterator_facade</span></tt>'s <tt class="literal"><span class="pre">Derived</span></tt> parameter, depending on the
iterator concept(s) it will model. The operations in the first iterator concept(s) it will model. The operations in the first
@ -464,7 +464,7 @@ Iterator</td>
</div> </div>
<a class="target" id="facade-iterator-category" name="facade-iterator-category"></a></div> <a class="target" id="facade-iterator-category" name="facade-iterator-category"></a></div>
<div class="section" id="iterator-facade-iterator-category"> <div class="section" id="iterator-facade-iterator-category">
<h2><a class="toc-backref" href="#id28" name="iterator-facade-iterator-category"><tt class="literal"><span class="pre">iterator_facade</span></tt> iterator category</a></h2> <h2><a class="toc-backref" href="#id27" name="iterator-facade-iterator-category"><tt class="literal"><span class="pre">iterator_facade</span></tt> iterator category</a></h2>
<p>The <tt class="literal"><span class="pre">iterator_category</span></tt> member of <tt class="literal"><span class="pre">iterator_facade&lt;X,V,R,C,D&gt;</span></tt> <p>The <tt class="literal"><span class="pre">iterator_category</span></tt> member of <tt class="literal"><span class="pre">iterator_facade&lt;X,V,R,C,D&gt;</span></tt>
is a type which satisfies the following conditions:</p> is a type which satisfies the following conditions:</p>
<blockquote> <blockquote>
@ -517,7 +517,7 @@ convertible, and not to any more-derived traversal tag type.</p>
</blockquote> </blockquote>
</div> </div>
<div class="section" id="iterator-facade-operations"> <div class="section" id="iterator-facade-operations">
<h2><a class="toc-backref" href="#id29" name="iterator-facade-operations"><tt class="literal"><span class="pre">iterator_facade</span></tt> operations</a></h2> <h2><a class="toc-backref" href="#id28" name="iterator-facade-operations"><tt class="literal"><span class="pre">iterator_facade</span></tt> operations</a></h2>
<p>The operations in this section are described in terms of operations on <p>The operations in this section are described in terms of operations on
the core interface of <tt class="literal"><span class="pre">Derived</span></tt> which may be inaccessible the core interface of <tt class="literal"><span class="pre">Derived</span></tt> which may be inaccessible
(i.e. private). The implementation should access these operations (i.e. private). The implementation should access these operations
@ -659,7 +659,7 @@ return tmp -= n;
</div> </div>
</div> </div>
<div class="section" id="tutorial-example"> <div class="section" id="tutorial-example">
<h1><a class="toc-backref" href="#id30" name="tutorial-example">Tutorial Example</a></h1> <h1><a class="toc-backref" href="#id29" name="tutorial-example">Tutorial Example</a></h1>
<!-- Copyright David Abrahams 2004. Use, modification and distribution is --> <!-- Copyright David Abrahams 2004. Use, modification and distribution is -->
<!-- subject to the Boost Software License, Version 1.0. (See accompanying --> <!-- 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) --> <!-- file LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt) -->
@ -669,7 +669,7 @@ example of a linked list of polymorphic objects. This example was
inspired by a <a class="reference" href="http://thread.gmane.org/gmane.comp.lib.boost.user/5100">posting</a> by Keith Macdonald on the <a class="reference" href="../../../more/mailing_lists.htm#users">Boost-Users</a> inspired by a <a class="reference" href="http://thread.gmane.org/gmane.comp.lib.boost.user/5100">posting</a> by Keith Macdonald on the <a class="reference" href="../../../more/mailing_lists.htm#users">Boost-Users</a>
mailing list.</p> mailing list.</p>
<div class="section" id="the-problem"> <div class="section" id="the-problem">
<h2><a class="toc-backref" href="#id31" name="the-problem">The Problem</a></h2> <h2><a class="toc-backref" href="#id30" name="the-problem">The Problem</a></h2>
<p>Say we've written a polymorphic linked list node base class:</p> <p>Say we've written a polymorphic linked list node base class:</p>
<pre class="literal-block"> <pre class="literal-block">
# include &lt;iostream&gt; # include &lt;iostream&gt;
@ -731,7 +731,7 @@ inline std::ostream&amp; operator&lt;&lt;(std::ostream&amp; s, node_base const&a
lists.</p> lists.</p>
</div> </div>
<div class="section" id="a-basic-iterator-using-iterator-facade"> <div class="section" id="a-basic-iterator-using-iterator-facade">
<h2><a class="toc-backref" href="#id32" name="a-basic-iterator-using-iterator-facade">A Basic Iterator Using <tt class="literal"><span class="pre">iterator_facade</span></tt></a></h2> <h2><a class="toc-backref" href="#id31" name="a-basic-iterator-using-iterator-facade">A Basic Iterator Using <tt class="literal"><span class="pre">iterator_facade</span></tt></a></h2>
<p>We will construct a <tt class="literal"><span class="pre">node_iterator</span></tt> class using inheritance from <p>We will construct a <tt class="literal"><span class="pre">node_iterator</span></tt> class using inheritance from
<tt class="literal"><span class="pre">iterator_facade</span></tt> to implement most of the iterator's operations.</p> <tt class="literal"><span class="pre">iterator_facade</span></tt> to implement most of the iterator's operations.</p>
<pre class="literal-block"> <pre class="literal-block">
@ -745,24 +745,24 @@ class node_iterator
}; };
</pre> </pre>
<div class="section" id="template-arguments-for-iterator-facade"> <div class="section" id="template-arguments-for-iterator-facade">
<h3><a class="toc-backref" href="#id33" name="template-arguments-for-iterator-facade">Template Arguments for <tt class="literal"><span class="pre">iterator_facade</span></tt></a></h3> <h3><a class="toc-backref" href="#id32" name="template-arguments-for-iterator-facade">Template Arguments for <tt class="literal"><span class="pre">iterator_facade</span></tt></a></h3>
<p><tt class="literal"><span class="pre">iterator_facade</span></tt> has several template parameters, so we must decide <p><tt class="literal"><span class="pre">iterator_facade</span></tt> has several template parameters, so we must decide
what types to use for the arguments. The parameters are <tt class="literal"><span class="pre">Derived</span></tt>, what types to use for the arguments. The parameters are <tt class="literal"><span class="pre">Derived</span></tt>,
<tt class="literal"><span class="pre">Value</span></tt>, <tt class="literal"><span class="pre">CategoryOrTraversal</span></tt>, <tt class="literal"><span class="pre">Reference</span></tt>, and <tt class="literal"><span class="pre">Difference</span></tt>.</p> <tt class="literal"><span class="pre">Value</span></tt>, <tt class="literal"><span class="pre">CategoryOrTraversal</span></tt>, <tt class="literal"><span class="pre">Reference</span></tt>, and <tt class="literal"><span class="pre">Difference</span></tt>.</p>
<div class="section" id="derived"> <div class="section" id="derived">
<h4><a class="toc-backref" href="#id34" name="derived"><tt class="literal"><span class="pre">Derived</span></tt></a></h4> <h4><a class="toc-backref" href="#id33" name="derived"><tt class="literal"><span class="pre">Derived</span></tt></a></h4>
<p>Because <tt class="literal"><span class="pre">iterator_facade</span></tt> is meant to be used with the CRTP <p>Because <tt class="literal"><span class="pre">iterator_facade</span></tt> is meant to be used with the CRTP
<a class="citation-reference" href="#cop95" id="id8" name="id8">[Cop95]</a> the first parameter is the iterator class name itself, <a class="citation-reference" href="#cop95" id="id8" name="id8">[Cop95]</a> the first parameter is the iterator class name itself,
<tt class="literal"><span class="pre">node_iterator</span></tt>.</p> <tt class="literal"><span class="pre">node_iterator</span></tt>.</p>
</div> </div>
<div class="section" id="value"> <div class="section" id="value">
<h4><a class="toc-backref" href="#id35" name="value"><tt class="literal"><span class="pre">Value</span></tt></a></h4> <h4><a class="toc-backref" href="#id34" name="value"><tt class="literal"><span class="pre">Value</span></tt></a></h4>
<p>The <tt class="literal"><span class="pre">Value</span></tt> parameter determines the <tt class="literal"><span class="pre">node_iterator</span></tt>'s <p>The <tt class="literal"><span class="pre">Value</span></tt> parameter determines the <tt class="literal"><span class="pre">node_iterator</span></tt>'s
<tt class="literal"><span class="pre">value_type</span></tt>. In this case, we are iterating over <tt class="literal"><span class="pre">node_base</span></tt> <tt class="literal"><span class="pre">value_type</span></tt>. In this case, we are iterating over <tt class="literal"><span class="pre">node_base</span></tt>
objects, so <tt class="literal"><span class="pre">Value</span></tt> will be <tt class="literal"><span class="pre">node_base</span></tt>.</p> objects, so <tt class="literal"><span class="pre">Value</span></tt> will be <tt class="literal"><span class="pre">node_base</span></tt>.</p>
</div> </div>
<div class="section" id="categoryortraversal"> <div class="section" id="categoryortraversal">
<h4><a class="toc-backref" href="#id36" name="categoryortraversal"><tt class="literal"><span class="pre">CategoryOrTraversal</span></tt></a></h4> <h4><a class="toc-backref" href="#id35" name="categoryortraversal"><tt class="literal"><span class="pre">CategoryOrTraversal</span></tt></a></h4>
<p>Now we have to determine which <a class="reference" href="new-iter-concepts.html#iterator-traversal-concepts-lib-iterator-traversal">iterator traversal concept</a> our <p>Now we have to determine which <a class="reference" href="new-iter-concepts.html#iterator-traversal-concepts-lib-iterator-traversal">iterator traversal concept</a> our
<tt class="literal"><span class="pre">node_iterator</span></tt> is going to model. Singly-linked lists only have <tt class="literal"><span class="pre">node_iterator</span></tt> is going to model. Singly-linked lists only have
forward links, so our iterator can't can't be a <a class="reference" href="new-iter-concepts.html#bidirectional-traversal-iterators-lib-bidirectional-traversal-iterators">bidirectional forward links, so our iterator can't can't be a <a class="reference" href="new-iter-concepts.html#bidirectional-traversal-iterators-lib-bidirectional-traversal-iterators">bidirectional
@ -782,7 +782,7 @@ end up being <tt class="literal"><span class="pre">std::forward_iterator_tag</sp
</table> </table>
</div> </div>
<div class="section" id="id10"> <div class="section" id="id10">
<h4><a class="toc-backref" href="#id37" name="id10"><tt class="literal"><span class="pre">Reference</span></tt></a></h4> <h4><a class="toc-backref" href="#id36" name="id10"><tt class="literal"><span class="pre">Reference</span></tt></a></h4>
<p>The <tt class="literal"><span class="pre">Reference</span></tt> argument becomes the type returned by <p>The <tt class="literal"><span class="pre">Reference</span></tt> argument becomes the type returned by
<tt class="literal"><span class="pre">node_iterator</span></tt>'s dereference operation, and will also be the <tt class="literal"><span class="pre">node_iterator</span></tt>'s dereference operation, and will also be the
same as <tt class="literal"><span class="pre">std::iterator_traits&lt;node_iterator&gt;::reference</span></tt>. The same as <tt class="literal"><span class="pre">std::iterator_traits&lt;node_iterator&gt;::reference</span></tt>. The
@ -791,7 +791,7 @@ library's default for this parameter is <tt class="literal"><span class="pre">Va
type, we can omit this argument, or pass <tt class="literal"><span class="pre">use_default</span></tt>.</p> type, we can omit this argument, or pass <tt class="literal"><span class="pre">use_default</span></tt>.</p>
</div> </div>
<div class="section" id="difference"> <div class="section" id="difference">
<h4><a class="toc-backref" href="#id38" name="difference"><tt class="literal"><span class="pre">Difference</span></tt></a></h4> <h4><a class="toc-backref" href="#id37" name="difference"><tt class="literal"><span class="pre">Difference</span></tt></a></h4>
<p>The <tt class="literal"><span class="pre">Difference</span></tt> argument determines how the distance between <p>The <tt class="literal"><span class="pre">Difference</span></tt> argument determines how the distance between
two <tt class="literal"><span class="pre">node_iterator</span></tt>s will be measured and will also be the two <tt class="literal"><span class="pre">node_iterator</span></tt>s will be measured and will also be the
same as <tt class="literal"><span class="pre">std::iterator_traits&lt;node_iterator&gt;::difference_type</span></tt>. same as <tt class="literal"><span class="pre">std::iterator_traits&lt;node_iterator&gt;::difference_type</span></tt>.
@ -818,7 +818,7 @@ class node_iterator
</div> </div>
</div> </div>
<div class="section" id="constructors-and-data-members"> <div class="section" id="constructors-and-data-members">
<h3><a class="toc-backref" href="#id39" name="constructors-and-data-members">Constructors and Data Members</a></h3> <h3><a class="toc-backref" href="#id38" name="constructors-and-data-members">Constructors and Data Members</a></h3>
<p>Next we need to decide how to represent the iterator's position. <p>Next we need to decide how to represent the iterator's position.
This representation will take the form of data members, so we'll This representation will take the form of data members, so we'll
also need to write constructors to initialize them. The also need to write constructors to initialize them. The
@ -862,8 +862,8 @@ default constructor to leave <tt class="literal"><span class="pre">m_node</span>
</tbody> </tbody>
</table> </table>
</div> </div>
<div class="section" id="id12"> <div class="section" id="implementing-the-core-operations">
<h3><a class="toc-backref" href="#id40" name="id12">Core Operations</a></h3> <h3><a class="toc-backref" href="#id39" name="implementing-the-core-operations">Implementing the Core Operations</a></h3>
<p>The last step is to implement the <a class="reference" href="#core-operations">core operations</a> required by <p>The last step is to implement the <a class="reference" href="#core-operations">core operations</a> required by
the concepts we want our iterator to model. Referring to the the concepts we want our iterator to model. Referring to the
<a class="reference" href="#core-operations">table</a>, we can see that the first three rows are applicable <a class="reference" href="#core-operations">table</a>, we can see that the first three rows are applicable
@ -914,7 +914,7 @@ iterator! For a working example of its use, see <a class="reference" href="../e
</div> </div>
</div> </div>
<div class="section" id="a-constant-node-iterator"> <div class="section" id="a-constant-node-iterator">
<h2><a class="toc-backref" href="#id41" name="a-constant-node-iterator">A constant <tt class="literal"><span class="pre">node_iterator</span></tt></a></h2> <h2><a class="toc-backref" href="#id40" name="a-constant-node-iterator">A constant <tt class="literal"><span class="pre">node_iterator</span></tt></a></h2>
<div class="sidebar"> <div class="sidebar">
<p class="sidebar-title">Constant and Mutable iterators</p> <p class="sidebar-title">Constant and Mutable iterators</p>
<p>The term <strong>mutable iterator</strong> means an iterator through which <p>The term <strong>mutable iterator</strong> means an iterator through which
@ -1015,7 +1015,7 @@ typedef node_iter&lt;node_base const&gt; node_const_iterator;
</pre> </pre>
</div> </div>
<div class="section" id="interoperability"> <div class="section" id="interoperability">
<h2><a class="toc-backref" href="#id42" name="interoperability">Interoperability</a></h2> <h2><a class="toc-backref" href="#id41" name="interoperability">Interoperability</a></h2>
<p>Our <tt class="literal"><span class="pre">const_node_iterator</span></tt> works perfectly well on its own, but <p>Our <tt class="literal"><span class="pre">const_node_iterator</span></tt> works perfectly well on its own, but
taken together with <tt class="literal"><span class="pre">node_iterator</span></tt> it doesn't quite meet taken together with <tt class="literal"><span class="pre">node_iterator</span></tt> it doesn't quite meet
expectations. For example, we'd like to be able to pass a expectations. For example, we'd like to be able to pass a
@ -1027,7 +1027,7 @@ compare them for equality.</p>
<p>This expected ability to use two different iterator types together <p>This expected ability to use two different iterator types together
is known as <strong>interoperability</strong>. Achieving interoperability in is known as <strong>interoperability</strong>. Achieving interoperability in
our case is as simple as templatizing the <tt class="literal"><span class="pre">equal</span></tt> function and our case is as simple as templatizing the <tt class="literal"><span class="pre">equal</span></tt> function and
adding a templatized converting constructor <a class="footnote-reference" href="#broken" id="id15" name="id15"><sup>3</sup></a> <a class="footnote-reference" href="#random" id="id16" name="id16"><sup>4</sup></a>:</p> adding a templatized converting constructor <a class="footnote-reference" href="#broken" id="id14" name="id14"><sup>3</sup></a> <a class="footnote-reference" href="#random" id="id15" name="id15"><sup>4</sup></a>:</p>
<pre class="literal-block"> <pre class="literal-block">
template &lt;class Value&gt; template &lt;class Value&gt;
class node_iter class node_iter
@ -1072,14 +1072,14 @@ typedef impl::node_iterator&lt;node_base const&gt; node_const_iterator;
<table class="footnote" frame="void" id="broken" rules="none"> <table class="footnote" frame="void" id="broken" rules="none">
<colgroup><col class="label" /><col /></colgroup> <colgroup><col class="label" /><col /></colgroup>
<tbody valign="top"> <tbody valign="top">
<tr><td class="label"><a class="fn-backref" href="#id15" name="broken">[3]</a></td><td>If you're using an older compiler and it can't handle <tr><td class="label"><a class="fn-backref" href="#id14" name="broken">[3]</a></td><td>If you're using an older compiler and it can't handle
this example, see the <a class="reference" href="../example/node_iterator2.hpp">example code</a> for workarounds.</td></tr> this example, see the <a class="reference" href="../example/node_iterator2.hpp">example code</a> for workarounds.</td></tr>
</tbody> </tbody>
</table> </table>
<table class="footnote" frame="void" id="random" rules="none"> <table class="footnote" frame="void" id="random" rules="none">
<colgroup><col class="label" /><col /></colgroup> <colgroup><col class="label" /><col /></colgroup>
<tbody valign="top"> <tbody valign="top">
<tr><td class="label"><a class="fn-backref" href="#id16" name="random">[4]</a></td><td>If <tt class="literal"><span class="pre">node_iterator</span></tt> had been a <a class="reference" href="new-iter-concepts.html#random-access-traversal-iterators-lib-random-access-traversal-iterators">random access <tr><td class="label"><a class="fn-backref" href="#id15" name="random">[4]</a></td><td>If <tt class="literal"><span class="pre">node_iterator</span></tt> had been a <a class="reference" href="new-iter-concepts.html#random-access-traversal-iterators-lib-random-access-traversal-iterators">random access
traversal iterator</a>, we'd have had to templatize its traversal iterator</a>, we'd have had to templatize its
<tt class="literal"><span class="pre">distance_to</span></tt> function as well.</td></tr> <tt class="literal"><span class="pre">distance_to</span></tt> function as well.</td></tr>
</tbody> </tbody>
@ -1088,7 +1088,7 @@ traversal iterator</a>, we'd have had to templatize its
iterators <a class="reference" href="../example/node_iterator2.cpp">here</a>.</p> iterators <a class="reference" href="../example/node_iterator2.cpp">here</a>.</p>
</div> </div>
<div class="section" id="telling-the-truth"> <div class="section" id="telling-the-truth">
<h2><a class="toc-backref" href="#id43" name="telling-the-truth">Telling the Truth</a></h2> <h2><a class="toc-backref" href="#id42" name="telling-the-truth">Telling the Truth</a></h2>
<p>Now <tt class="literal"><span class="pre">node_iterator</span></tt> and <tt class="literal"><span class="pre">node_const_iterator</span></tt> behave exactly as <p>Now <tt class="literal"><span class="pre">node_iterator</span></tt> and <tt class="literal"><span class="pre">node_const_iterator</span></tt> behave exactly as
you'd expect... almost. We can compare them and we can convert in you'd expect... almost. We can compare them and we can convert in
one direction: from <tt class="literal"><span class="pre">node_iterator</span></tt> to <tt class="literal"><span class="pre">node_const_iterator</span></tt>. one direction: from <tt class="literal"><span class="pre">node_iterator</span></tt> to <tt class="literal"><span class="pre">node_const_iterator</span></tt>.
@ -1109,19 +1109,24 @@ the <tt class="literal"><span class="pre">m_node</span></tt> conversion would fa
follows, we can remove it from the overload set when it's not follows, we can remove it from the overload set when it's not
appropriate:</p> appropriate:</p>
<pre class="literal-block"> <pre class="literal-block">
template &lt;class OtherValue&gt; #include &lt;boost/type_traits/is_convertible.hpp&gt;
node_iter( #include &lt;boost/utility/enable_if.hpp&gt;
node_iter&lt;OtherValue&gt; const&amp; other
, typename boost::enable_if&lt; ...
boost::is_convertible&lt;OtherValue*,Value*&gt;
, enabler template &lt;class OtherValue&gt;
&gt;::type = enabler() node_iter(
) node_iter&lt;OtherValue&gt; const&amp; other
: m_node(other.m_node) {} , typename boost::enable_if&lt;
boost::is_convertible&lt;OtherValue*,Value*&gt;
, enabler
&gt;::type = enabler()
)
: m_node(other.m_node) {}
</pre> </pre>
</div> </div>
<div class="section" id="wrap-up"> <div class="section" id="wrap-up">
<h2><a class="toc-backref" href="#id44" name="wrap-up">Wrap Up</a></h2> <h2><a class="toc-backref" href="#id43" name="wrap-up">Wrap Up</a></h2>
<p>This concludes our <tt class="literal"><span class="pre">iterator_facade</span></tt> tutorial, but before you <p>This concludes our <tt class="literal"><span class="pre">iterator_facade</span></tt> tutorial, but before you
stop reading we urge you to take a look at <a class="reference" href="iterator_adaptor.html"><tt class="literal"><span class="pre">iterator_adaptor</span></tt></a>. stop reading we urge you to take a look at <a class="reference" href="iterator_adaptor.html"><tt class="literal"><span class="pre">iterator_adaptor</span></tt></a>.
There's another way to approach writing these iterators which might There's another way to approach writing these iterators which might
@ -1132,7 +1137,7 @@ even be superior.</p>
<hr class="footer" /> <hr class="footer" />
<div class="footer"> <div class="footer">
<a class="reference" href="iterator_facade.rst">View document source</a>. <a class="reference" href="iterator_facade.rst">View document source</a>.
Generated on: 2004-01-12 17:28 UTC. Generated on: 2004-01-12 19:20 UTC.
Generated by <a class="reference" href="http://docutils.sourceforge.net/">Docutils</a> from <a class="reference" href="http://docutils.sourceforge.net/rst.html">reStructuredText</a> source. Generated by <a class="reference" href="http://docutils.sourceforge.net/">Docutils</a> from <a class="reference" href="http://docutils.sourceforge.net/rst.html">reStructuredText</a> source.
</div> </div>
</body> </body>

View File

@ -212,8 +212,8 @@ Our ``node_iterator`` then becomes::
really concerned with efficiency, we could've written the really concerned with efficiency, we could've written the
default constructor to leave ``m_node`` uninitialized. default constructor to leave ``m_node`` uninitialized.
Core Operations Implementing the Core Operations
............... ................................
The last step is to implement the `core operations`_ required by The last step is to implement the `core operations`_ required by
the concepts we want our iterator to model. Referring to the the concepts we want our iterator to model. Referring to the
@ -475,6 +475,11 @@ In fact, that sort of magic is possible using
follows, we can remove it from the overload set when it's not follows, we can remove it from the overload set when it's not
appropriate:: appropriate::
#include <boost/type_traits/is_convertible.hpp>
#include <boost/utility/enable_if.hpp>
...
template <class OtherValue> template <class OtherValue>
node_iter( node_iter(
node_iter<OtherValue> const& other node_iter<OtherValue> const& other

View File

@ -9,4 +9,5 @@ test-suite iterator_examples
: [ run reverse_iterator.cpp ] : [ run reverse_iterator.cpp ]
[ run node_iterator1.cpp ] [ run node_iterator1.cpp ]
[ run node_iterator2.cpp ] [ run node_iterator2.cpp ]
[ run node_iterator3.cpp ]
; ;

View File

@ -5,7 +5,7 @@
# define NODE_ITERATOR2_DWA2004110_HPP # define NODE_ITERATOR2_DWA2004110_HPP
# include "node.hpp" # include "node.hpp"
# include <boost/iterator/iterator_facade.hpp> # include <boost/iterator/iterator_adaptor.hpp>
# ifndef BOOST_NO_SFINAE # ifndef BOOST_NO_SFINAE
# include <boost/type_traits/is_convertible.hpp> # include <boost/type_traits/is_convertible.hpp>
@ -14,21 +14,26 @@
template <class Value> template <class Value>
class node_iter class node_iter
: public boost::iterator_facade< : public boost::iterator_adaptor<
node_iter<Value> node_iter<Value> // Derived
, Value , Value* // Base
, boost::forward_traversal_tag , boost::use_default // Value
, boost::forward_traversal_tag // CategoryOrTraversal
> >
{ {
private: private:
struct enabler {}; // a private type avoids misuse struct enabler {}; // a private type avoids misuse
typedef boost::iterator_adaptor<
node_iter<Value>, Value*, boost::use_default, boost::forward_traversal_tag
> super_t;
public: public:
node_iter() node_iter()
: m_node(0) {} : super_t(0) {}
explicit node_iter(Value* p) explicit node_iter(Value* p)
: m_node(p) {} : super_t(p) {}
template <class OtherValue> template <class OtherValue>
node_iter( node_iter(
@ -42,29 +47,9 @@ class node_iter
) )
: m_node(other.m_node) {} : m_node(other.m_node) {}
# if !BOOST_WORKAROUND(__GNUC__, == 2)
private: // GCC2 can't even grant that friendship to template member functions
# endif
friend class boost::iterator_core_access;
template <class OtherValue>
bool equal(node_iter<OtherValue> const& other) const
{
return this->m_node == other.m_node;
}
private: private:
friend class boost::iterator_core_access;
void increment() { m_node = m_node->next(); } void increment() { m_node = m_node->next(); }
Value& dereference() const { return *m_node; }
# ifdef BOOST_NO_MEMBER_TEMPLATE_FRIENDS
public:
# else
template <class> friend class node_iter;
# endif
Value* m_node;
}; };
typedef node_iter<node_base> node_iterator; typedef node_iter<node_base> node_iterator;

43
example/node_iterator3.cpp Executable file
View File

@ -0,0 +1,43 @@
// Copyright David Abrahams 2004. 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 "node_iterator3.hpp"
#include <string>
#include <memory>
#include <iostream>
#include <algorithm>
#include <boost/mem_fn.hpp>
#include <cassert>
int main()
{
std::auto_ptr<node<int> > nodes(new node<int>(42));
nodes->append(new node<std::string>(" is greater than "));
nodes->append(new node<int>(13));
// Check interoperability
assert(node_iterator(nodes.get()) == node_const_iterator(nodes.get()));
assert(node_const_iterator(nodes.get()) == node_iterator(nodes.get()));
assert(node_iterator(nodes.get()) != node_const_iterator());
assert(node_const_iterator(nodes.get()) != node_iterator());
std::copy(
node_iterator(nodes.get()), node_iterator()
, std::ostream_iterator<node_base>(std::cout, " ")
);
std::cout << std::endl;
std::for_each(
node_iterator(nodes.get()), node_iterator()
, boost::mem_fn(&node_base::double_me)
);
std::copy(
node_const_iterator(nodes.get()), node_const_iterator()
, std::ostream_iterator<node_base>(std::cout, "/")
);
std::cout << std::endl;
return 0;
}

58
example/node_iterator3.hpp Executable file
View File

@ -0,0 +1,58 @@
// Copyright David Abrahams 2004. 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 NODE_ITERATOR3_DWA2004110_HPP
# define NODE_ITERATOR3_DWA2004110_HPP
# include "node.hpp"
# include <boost/iterator/iterator_adaptor.hpp>
# ifndef BOOST_NO_SFINAE
# include <boost/type_traits/is_convertible.hpp>
# include <boost/utility/enable_if.hpp>
# endif
template <class Value>
class node_iter
: public boost::iterator_adaptor<
node_iter<Value> // Derived
, Value* // Base
, boost::use_default // Value
, boost::forward_traversal_tag // CategoryOrTraversal
>
{
private:
struct enabler {}; // a private type avoids misuse
typedef boost::iterator_adaptor<
node_iter<Value>, Value*, boost::use_default, boost::forward_traversal_tag
> super_t;
public:
node_iter()
: super_t(0) {}
explicit node_iter(Value* p)
: super_t(p) {}
template <class OtherValue>
node_iter(
node_iter<OtherValue> const& other
# ifndef BOOST_NO_SFINAE
, typename boost::enable_if<
boost::is_convertible<OtherValue*,Value*>
, enabler
>::type = enabler()
# endif
)
: m_node(other.m_node) {}
private:
friend class boost::iterator_core_access;
void increment() { this->base_reference() = this->base()->next(); }
};
typedef node_iter<node_base> node_iterator;
typedef node_iter<node_base const> node_const_iterator;
#endif // NODE_ITERATOR3_DWA2004110_HPP