Aleph-w 3.0
A C++ Library for Data Structures and Algorithms
Loading...
Searching...
No Matches
Aleph::Generator< T > Class Template Reference

Lazy, single-pass sequence of T values produced by a coroutine. More...

#include <ah-generator.H>

Classes

class  iterator
 Single-pass input iterator over the yielded sequence. More...
 
struct  promise_type
 The promise type the compiler instantiates for a coroutine returning Generator<T>. More...
 

Public Types

using Handle = std::coroutine_handle< promise_type >
 

Public Member Functions

 Generator () noexcept=default
 Construct an empty/singular Generator (no coroutine attached).
 
 Generator (Handle h) noexcept
 Construct from a coroutine handle (internal use by promise_type).
 
 Generator (const Generator &)=delete
 Deleted: a Generator owns a single coroutine frame, which cannot be duplicated.
 
Generator & operator= (const Generator &)=delete
 Deleted: see the copy constructor.
 
 Generator (Generator &&o) noexcept
 Move constructor: transfers coroutine-frame ownership.
 
Generator & operator= (Generator &&o) noexcept
 Move assignment: destroys any owned frame, then steals o's.
 
 ~Generator ()
 Destroys the coroutine frame, if any, unwinding pending local state inside the (possibly still-suspended) coroutine body.
 
iterator begin () &
 Begin iterating: resumes the coroutine to its first co_yield.
 

Static Public Member Functions

static std::default_sentinel_t end () noexcept
 End sentinel, per the C++20 sentinel-based range model.
 

Private Attributes

Handle handle_ {}
 

Detailed Description

template<class T>
class Aleph::Generator< T >

Lazy, single-pass sequence of T values produced by a coroutine.

A function returning Aleph::Generator<T> and using co_yield in its body is a generator function: calling it does not run the body — it creates a suspended coroutine frame. The body advances one co_yield at a time as the sequence is iterated (range-for, begin()/operator++, or manual resume()/value()).

Template Parameters
TType of the yielded values. co_yield accepts lvalues and rvalues convertible to std::remove_reference_t<T>; the iterator exposes the currently yielded object by reference.
Yielded value lifetime
Dereferencing the iterator returns a reference to the object currently suspended at co_yield. That reference is valid only until the generator is resumed again (operator++() or a second begin()), or until the Generator is destroyed. Copy or move the value out if it must survive beyond the current iteration step.
Iteration model
Aleph::Generator<T> models a C++ input range: begin() resumes the coroutine to its first co_yield (or to completion, if the body never yields) and returns an iterator; end() returns std::default_sentinel. The iterator is single-pass — advancing it resumes the underlying coroutine, so only one iterator on a given Generator should be advanced at a time. Copying a Generator is disallowed (it owns the coroutine frame); move it instead.
Exception propagation
An exception thrown inside the coroutine body is captured and rethrown from the call that resumed the coroutine (operator++ or begin() for the first element) — exactly where a hand-written iterator would throw.
Early termination
Destroying the Generator (or letting it go out of scope) before it is exhausted destroys the coroutine frame and unwinds any pending stack frames inside the coroutine body — co_yield sits inside ordinary C++ control flow, so local objects along that path are destroyed normally.
Thread Safety
A single Generator<T> instance is not thread-safe: it owns one suspended coroutine frame with no synchronization. Distinct instances (including ones produced by concurrent calls to the same generator function) may be driven from distinct threads.
Example
{
for (int i = lo; i < hi; ++i)
co_yield i;
}
int total = 0;
for (int x : range(0, 5))
total += x; // 0+1+2+3+4 == 10, computed lazily
Lazy, single-pass sequence of T values produced by a coroutine.
size_t blossom_maximum_cardinality_matching(const GT &g, DynDlist< typename GT::Arc * > &matching, SA sa=SA())
Alias of compute_maximum_cardinality_general_matching().
Definition Blossom.H:466
Container< T > range(const T start, const T end, const T step=1)
Generate a range of values [start, end] with a given step.

Definition at line 152 of file ah-generator.H.

Member Typedef Documentation

◆ Handle

template<class T >
using Aleph::Generator< T >::Handle = std::coroutine_handle<promise_type>

Definition at line 208 of file ah-generator.H.

Constructor & Destructor Documentation

◆ Generator() [1/4]

template<class T >
Aleph::Generator< T >::Generator ( )
defaultnoexcept

Construct an empty/singular Generator (no coroutine attached).

◆ Generator() [2/4]

template<class T >
Aleph::Generator< T >::Generator ( Handle  h)
inlineexplicitnoexcept

Construct from a coroutine handle (internal use by promise_type).

Definition at line 293 of file ah-generator.H.

◆ Generator() [3/4]

template<class T >
Aleph::Generator< T >::Generator ( const Generator< T > &  )
delete

Deleted: a Generator owns a single coroutine frame, which cannot be duplicated.

Move it instead.

◆ Generator() [4/4]

template<class T >
Aleph::Generator< T >::Generator ( Generator< T > &&  o)
inlinenoexcept

Move constructor: transfers coroutine-frame ownership.

Definition at line 303 of file ah-generator.H.

◆ ~Generator()

template<class T >
Aleph::Generator< T >::~Generator ( )
inline

Destroys the coroutine frame, if any, unwinding pending local state inside the (possibly still-suspended) coroutine body.

Definition at line 319 of file ah-generator.H.

References Aleph::Generator< T >::handle_.

Member Function Documentation

◆ begin()

template<class T >
iterator Aleph::Generator< T >::begin ( ) &
inline

Begin iterating: resumes the coroutine to its first co_yield.

Returns
An iterator positioned at the first value (or already end() if the body never yields, was already exhausted, or this is a default-constructed/moved-from Generator with no coroutine attached — an "empty/singular" Generator iterates zero times rather than throwing, matching the usual empty-range/empty- container convention).
Exceptions
Whateverthe coroutine body throws before its first co_yield, if anything.
Note
begin() is lvalue-qualified on purpose: range-for over a temporary generator is safe because the loop binds the temporary to a hidden local variable, but a direct make_generator().begin() would leave the returned iterator pointing at a destroyed coroutine frame. That direct call is therefore a compile-time error.
Calling begin() more than once while the sequence is still mid-traversal resumes the coroutine again, which is almost certainly not what you want on a single-pass sequence; iterate it exactly once. Calling it again after the sequence is exhausted is safe and simply returns end(): resuming a coroutine past its final suspend point is undefined behavior, so that case is detected and the resume is skipped instead.

Definition at line 347 of file ah-generator.H.

References Aleph::and, Aleph::blossom_maximum_cardinality_matching(), and Aleph::Generator< T >::handle_.

Referenced by TEST(), TEST(), TEST(), TEST(), TEST(), TEST(), and TEST().

◆ end()

template<class T >
static std::default_sentinel_t Aleph::Generator< T >::end ( )
inlinestaticnoexcept

End sentinel, per the C++20 sentinel-based range model.

Definition at line 359 of file ah-generator.H.

Referenced by TEST(), TEST(), TEST(), and TEST().

◆ operator=() [1/2]

template<class T >
Generator & Aleph::Generator< T >::operator= ( const Generator< T > &  )
delete

Deleted: see the copy constructor.

◆ operator=() [2/2]

template<class T >
Generator & Aleph::Generator< T >::operator= ( Generator< T > &&  o)
inlinenoexcept

Move assignment: destroys any owned frame, then steals o's.

Definition at line 306 of file ah-generator.H.

References Aleph::blossom_maximum_cardinality_matching(), and Aleph::Generator< T >::handle_.

Member Data Documentation

◆ handle_


The documentation for this class was generated from the following file: