Moved generator_iterator.hpp in iterator directory and modernized.

generator_iterator now uses decltype approach to deduce value and reference
types instead of the legacy result_type typedef, which was required to be
defined by the generator function.

The default constructor of generator_iterator now value initializes its
data members to avoid using uninitialized data.
This commit is contained in:
Andrey Semashev 2025-02-07 01:12:32 +03:00
parent 6e6def930f
commit d35869cd25
5 changed files with 113 additions and 89 deletions

View File

@ -15,7 +15,7 @@
<h1>Generator Iterator Adaptor</h1>
<p>Defined in header <a href=
"../../boost/generator_iterator.hpp">boost/generator_iterator.hpp</a></p>
"../../boost/iterator/generator_iterator.hpp">boost/iterator/generator_iterator.hpp</a></p>
<p>The generator iterator adaptor makes it easier to create custom input
iterators from 0-ary functions and function objects. The adaptor takes a
@ -33,9 +33,7 @@
<blockquote>
<pre>
namespace boost {
template &lt;class Generator&gt;
class generator_iterator_policies;
namespace iterators {
template &lt;class Generator&gt;
class generator_iterator_generator;
@ -43,6 +41,7 @@ namespace boost {
typename generator_iterator_generator&lt;Generator&gt;::type
make_generator_iterator(Generator &amp; gen);
}
}
</pre>
</blockquote>
<hr>
@ -60,8 +59,8 @@ template &lt;class Generator&gt;
class generator_iterator_generator
{
public:
typedef <i>unspecified</i> type; // the resulting generator iterator type
}
using type = <i>unspecified</i>; // the resulting generator iterator type
};
</pre>
<h3>Template Parameters</h3>
@ -78,8 +77,8 @@ public:
"http://www.sgi.com/tech/stl/Generator.html">Generator</a></tt></td>
<td>The generator (0-ary function object) type being wrapped. The
return type of the function must be defined as
<tt>Generator::result_type</tt>. The function object must be a model of
return type of the function is deduced automatically from its
<tt>operator()</tt>. The function object must be a model of
<a href=
"http://www.sgi.com/tech/stl/Generator.html">Generator</a>.</td>
</tr>
@ -122,14 +121,14 @@ make_generator_iterator(Generator &amp; gen);
<blockquote>
<pre>
#include &lt;iostream&gt;
#include &lt;boost/generator_iterator.hpp&gt;
#include &lt;boost/iterators/generator_iterator.hpp&gt;
class my_generator
{
public:
typedef int result_type;
using result_type = int;
my_generator() : state(0) { }
int operator()() { return ++state; }
result_type operator()() { return ++state; }
private:
int state;
};
@ -137,7 +136,7 @@ private:
int main()
{
my_generator gen;
boost::generator_iterator_generator&lt;my_generator&gt;::type it = boost::make_generator_iterator(gen);
auto it = boost::iterators::make_generator_iterator(gen);
for(int i = 0; i &lt; 10; ++i, ++it)
std::cout &lt;&lt; *it &lt;&lt; std::endl;
}

View File

@ -1,85 +1,14 @@
// (C) Copyright Jens Maurer 2001.
// (C) Copyright Andrey Semashev 2025.
// 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)
//
// Revision History:
// 15 Nov 2001 Jens Maurer
// created.
// See http://www.boost.org/libs/utility/iterator_adaptors.htm for documentation.
#ifndef BOOST_ITERATOR_ADAPTOR_GENERATOR_ITERATOR_HPP
#define BOOST_ITERATOR_ADAPTOR_GENERATOR_ITERATOR_HPP
#include <boost/iterator/iterator_facade.hpp>
#include <boost/ref.hpp>
// This is a deprecated header left for backward compatibility.
// Please use <boost/iterator/generator_iterator.hpp> instead.
namespace boost {
namespace iterators {
template<class Generator>
class generator_iterator
: public iterator_facade<
generator_iterator<Generator>
, typename Generator::result_type
, single_pass_traversal_tag
, typename Generator::result_type const&
>
{
typedef iterator_facade<
generator_iterator<Generator>
, typename Generator::result_type
, single_pass_traversal_tag
, typename Generator::result_type const&
> super_t;
public:
generator_iterator() {}
generator_iterator(Generator* g) : m_g(g), m_value((*m_g)()) {}
void increment()
{
m_value = (*m_g)();
}
const typename Generator::result_type&
dereference() const
{
return m_value;
}
bool equal(generator_iterator const& y) const
{
return this->m_g == y.m_g && this->m_value == y.m_value;
}
private:
Generator* m_g;
typename Generator::result_type m_value;
};
template<class Generator>
struct generator_iterator_generator
{
typedef generator_iterator<Generator> type;
};
template <class Generator>
inline generator_iterator<Generator>
make_generator_iterator(Generator& gen)
{
typedef generator_iterator<Generator> result_t;
return result_t(&gen);
}
} // namespace iterators
using iterators::generator_iterator;
using iterators::generator_iterator_generator;
using iterators::make_generator_iterator;
} // namespace boost
#include <boost/iterator/generator_iterator.hpp>
#endif // BOOST_ITERATOR_ADAPTOR_GENERATOR_ITERATOR_HPP

View File

@ -0,0 +1,96 @@
// (C) Copyright Jens Maurer 2001.
// 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)
//
// Revision History:
// 15 Nov 2001 Jens Maurer
// created.
// See http://www.boost.org/libs/utility/iterator_adaptors.htm for documentation.
#ifndef BOOST_ITERATOR_GENERATOR_ITERATOR_HPP_INCLUDED_
#define BOOST_ITERATOR_GENERATOR_ITERATOR_HPP_INCLUDED_
#include <memory>
#include <type_traits>
#include <boost/iterator/iterator_facade.hpp>
#include <boost/iterator/iterator_categories.hpp>
namespace boost {
namespace iterators {
template< typename Generator >
class generator_iterator :
public iterator_facade<
generator_iterator< Generator >,
decltype(std::declval< Generator& >()()),
single_pass_traversal_tag,
decltype(std::declval< Generator& >()()) const&
>
{
friend class iterator_core_access;
private:
using super_t = iterator_facade<
generator_iterator< Generator >,
decltype(std::declval< Generator& >()()),
single_pass_traversal_tag,
decltype(std::declval< Generator& >()()) const&
>;
public:
generator_iterator() :
m_g(nullptr),
m_value()
{}
generator_iterator(Generator* g) :
m_g(g),
m_value((*m_g)())
{}
private:
void increment()
{
m_value = (*m_g)();
}
typename super_t::reference dereference() const
{
return m_value;
}
bool equal(generator_iterator const& y) const
{
return m_g == y.m_g && m_value == y.m_value;
}
private:
Generator* m_g;
typename Generator::result_type m_value;
};
template< typename Generator >
struct generator_iterator_generator
{
using type = generator_iterator< Generator >;
};
template< typename Generator >
inline generator_iterator< Generator > make_generator_iterator(Generator& gen)
{
return generator_iterator< Generator >(std::addressof(gen));
}
} // namespace iterators
using iterators::generator_iterator;
using iterators::generator_iterator_generator;
using iterators::make_generator_iterator;
} // namespace boost
#endif // BOOST_ITERATOR_GENERATOR_ITERATOR_HPP_INCLUDED_

View File

@ -6,7 +6,7 @@
// http://www.boost.org/LICENSE_1_0.txt
//
#include <boost/generator_iterator.hpp>
#include <boost/iterator/generator_iterator.hpp>
#include <boost/core/lightweight_test.hpp>
#include <algorithm>

View File

@ -4,7 +4,6 @@
// See accompanying file LICENSE_1_0.txt or copy at
// https://www.boost.org/LICENSE_1_0.txt)
#include <boost/generator_iterator.hpp>
#include <boost/indirect_reference.hpp>
#include <boost/next_prior.hpp>
#include <boost/pointee.hpp>
@ -15,6 +14,7 @@
#include <boost/iterator/filter_iterator.hpp>
#include <boost/iterator/function_input_iterator.hpp>
#include <boost/iterator/function_output_iterator.hpp>
#include <boost/iterator/generator_iterator.hpp>
#include <boost/iterator/indirect_iterator.hpp>
#include <boost/iterator/interoperable.hpp>
#include <boost/iterator/is_iterator.hpp>