From 7b472a05ee736bbf40bb31a85d34fc5148e0ac6b Mon Sep 17 00:00:00 2001 From: Dave Abrahams Date: Sun, 1 Feb 2004 04:30:15 +0000 Subject: [PATCH] Obsoleted old iterator adaptor docs [SVN r22101] --- counting_iterator.htm | 325 ----------- filter_iterator.htm | 273 ---------- function_output_iterator.htm | 169 ------ indirect_iterator.htm | 444 --------------- iterator_adaptors.htm | 1000 ---------------------------------- iterator_adaptors.pdf | Bin 84856 -> 0 bytes iterator_adaptors.ppt | Bin 103936 -> 0 bytes permutation_iterator.htm | 177 ------ projection_iterator.htm | 391 ------------- reverse_iterator.htm | 331 ----------- transform_iterator.htm | 223 -------- 11 files changed, 3333 deletions(-) delete mode 100644 counting_iterator.htm delete mode 100644 filter_iterator.htm delete mode 100644 function_output_iterator.htm delete mode 100644 indirect_iterator.htm delete mode 100644 iterator_adaptors.htm delete mode 100644 iterator_adaptors.pdf delete mode 100644 iterator_adaptors.ppt delete mode 100644 permutation_iterator.htm delete mode 100644 projection_iterator.htm delete mode 100644 reverse_iterator.htm delete mode 100644 transform_iterator.htm diff --git a/counting_iterator.htm b/counting_iterator.htm deleted file mode 100644 index 0f6cb64..0000000 --- a/counting_iterator.htm +++ /dev/null @@ -1,325 +0,0 @@ - - - - - - -Counting Iterator Adaptor Documentation - - - - -c++boost.gif (8819 bytes) - -

Counting Iterator Adaptor

- -Defined in header -boost/counting_iterator.hpp - -

-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). The -following pseudo-code shows the general idea of how the -counting iterator is implemented. -

- -
-  // inside a hypothetical counting_iterator class...
-  typedef Incrementable value_type;
-  value_type counting_iterator::operator*() const {
-    return this->base; // no dereference!
-  }
-
- -All of the other operators of the counting iterator behave in the same -fashion as the Incrementable base type. - -

Synopsis

- -
-namespace boost {
-  template <class Incrementable>
-  struct counting_iterator_traits;
-
-  template <class Incrementable>
-  struct counting_iterator_generator;
-
-  template <class Incrementable>
-  typename counting_iterator_generator<Incrementable>::type
-  make_counting_iterator(Incrementable x);
-}
-
- -
- -

The Counting Iterator Type -Generator

- -The class template counting_iterator_generator<Incrementable> is a type generator for counting iterators. - -
-template <class Incrementable>
-class counting_iterator_generator
-{
-public:
-    typedef iterator_adaptor<...> type;
-};
-
- -

Example

- -In this example we use the counting iterator generator to create a -counting iterator, and count from zero to four. - -
-#include <boost/config.hpp>
-#include <iostream>
-#include <boost/counting_iterator.hpp>
-
-int main(int, char*[])
-{
-  // Example of using counting_iterator_generator
-  std::cout << "counting from 0 to 4:" << std::endl;
-  boost::counting_iterator_generator<int>::type first(0), last(4);
-  std::copy(first, last, std::ostream_iterator<int>(std::cout, " "));
-  std::cout << std::endl;
-
-  // to be continued...
-
-The output from this part is: -
-counting from 0 to 4:
-0 1 2 3 
-
- -

Template Parameters

- - - - - - - - - - - -
ParameterDescription
IncrementableThe type being wrapped by the adaptor.
- -

Model of

- -If the Incrementable type has all of the functionality of a -Random -Access Iterator except the operator*(), then the counting -iterator will be a model of Random -Access Iterator. If the Incrementable type has less -functionality, then the counting iterator will have correspondingly -less functionality. - -

Type Requirements

- -The Incrementable type must be Default -Constructible, Copy -Constructible, and Assignable. -Also, the Incrementable type must provide access to an -associated difference_type and iterator_category -through the counting_iterator_traits -class. - -

-Furthermore, if you wish to create a counting iterator that is a Forward -Iterator, then the following expressions must be valid: -

-Incrementable i, j;
-++i         // pre-increment
-i == j      // operator equal
-
-If you wish to create a counting iterator that is a -Bidirectional Iterator, then pre-decrement is also required: -
---i
-
-If you wish to create a counting iterator that is a Random -Access Iterator, then these additional expressions are also required: -
-counting_iterator_traits<Incrementable>::difference_type n;
-i += n
-n = i - j
-i < j
-
- - - -

Members

- -The counting iterator type implements the member functions and -operators required of the Random -Access Iterator concept. In addition it has the following -constructor: - -
-counting_iterator_generator::type(const Incrementable& i)
-
- -

-


-

- - -

The Counting Iterator Object Generator

- -
-template <class Incrementable>
-typename counting_iterator_generator<Incrementable>::type
-make_counting_iterator(Incrementable base);
-
- -An object -generator function that provides a convenient way to create counting -iterators.

- - - -

Example

- -In this example we count from negative five to positive five, this -time using the make_counting_iterator() function to save some -typing. - -
-  // continuing from previous example...
-
-  std::cout << "counting from -5 to 4:" << std::endl;
-  std::copy(boost::make_counting_iterator(-5),
-	    boost::make_counting_iterator(5),
-	    std::ostream_iterator<int>(std::cout, " "));
-  std::cout << std::endl;
-
-  // to be continued...
-
-The output from this part is: -
-counting from -5 to 4:
--5 -4 -3 -2 -1 0 1 2 3 4 
-
- -In the next example we create an array of numbers, and then create a -second array of pointers, where each pointer is the address of a -number in the first array. The counting iterator makes it easy to do -this since dereferencing a counting iterator that is wrapping an -iterator over the array of numbers just returns a pointer to the -current location in the array. We then use the indirect iterator adaptor to print -out the number in the array by accessing the numbers through the array -of pointers. - -
-  // continuing from previous example...
-
-  const int N = 7;
-  std::vector<int> numbers;
-  // Fill "numbers" array with [0,N)
-  std::copy(boost::make_counting_iterator(0), boost::make_counting_iterator(N),
-	    std::back_inserter(numbers));
-
-  std::vector<std::vector<int>::iterator> pointers;
-
-  // Use counting iterator to fill in the array of pointers.
-  std::copy(boost::make_counting_iterator(numbers.begin()),
-	    boost::make_counting_iterator(numbers.end()),
-	    std::back_inserter(pointers));
-
-  // Use indirect iterator to print out numbers by accessing
-  // them through the array of pointers.
-  std::cout << "indirectly printing out the numbers from 0 to " 
-	    << N << std::endl;
-  std::copy(boost::make_indirect_iterator(pointers.begin()),
-	    boost::make_indirect_iterator(pointers.end()),
-	    std::ostream_iterator<int>(std::cout, " "));
-  std::cout << std::endl;
-
-The output is: -
-indirectly printing out the numbers from 0 to 7
-0 1 2 3 4 5 6 
-
- -
- -

Counting Iterator Traits

- -The counting iterator adaptor needs to determine the appropriate -difference_type and iterator_category to use based on the -Incrementable type supplied by the user. The -counting_iterator_traits class provides these types. If the -Incrementable type is an integral type or an iterator, these types -will be correctly deduced by the counting_iterator_traits provided by -the library. Otherwise, the user must specialize -counting_iterator_traits for her type or add nested typedefs to -her type to fulfill the needs of - -std::iterator_traits. - -

The following pseudocode describes how the counting_iterator_traits are determined: - -

-template <class Incrementable>
-struct counting_iterator_traits
-{
-  if (numeric_limits<Incrementable>::is_specialized) {
-    if (!numeric_limits<Incrementable>::is_integer)
-       COMPILE_TIME_ERROR;
-
-    if (!numeric_limits<Incrementable>::is_bounded
-        && numeric_limits<Incrementable>::is_signed) {
-        typedef Incrementable difference_type;
-    }
-    else if (numeric_limits<Incrementable>::is_integral) {
-        typedef next-larger-signed-type-or-intmax_t difference_type;
-    }
-    typedef std::random_access_iterator_tag iterator_category;   
-  } else {
-    typedef std::iterator_traits<Incrementable>::difference_type difference_type;
-    typedef std::iterator_traits<Incrementable>::iterator_category iterator_category;
-  }
-};
-
- -

The italicized sections above are implementation details, but it is important -to know that the difference_type for integral types is selected so that -it can always represent the difference between two values if such a built-in -integer exists. On platforms with a working std::numeric_limits -implementation, the difference_type for any variable-length signed -integer type T is T itself. - -


-

Revised 19 Aug 2001

-

© Copyright Jeremy Siek 2000. Permission to copy, use, -modify, sell and distribute this document is granted provided this copyright -notice appears in all copies. This document is provided "as is" -without express or implied warranty, and with no claim as to its suitability for -any purpose.

- - - - - - - diff --git a/filter_iterator.htm b/filter_iterator.htm deleted file mode 100644 index 6c0c973..0000000 --- a/filter_iterator.htm +++ /dev/null @@ -1,273 +0,0 @@ - - - - - - -Filter Iterator Adaptor Documentation - - - - -c++boost.gif (8819 bytes) - -

Filter Iterator Adaptor

- -Defined in header -boost/iterator_adaptors.hpp - - -

-The filter iterator adaptor creates a view of an iterator range in -which some elements of the range are skipped over. A Predicate -function object controls which elements are skipped. When the -predicate is applied to an element, if it returns true then -the element is retained and if it returns false then the -element is skipped over. - - -

Synopsis

- -
-namespace boost {
-  template <class Predicate, class BaseIterator, ...>
-  class filter_iterator_generator;
-
-  template <class Predicate, class BaseIterator>
-  typename filter_iterator_generator<Predicate, BaseIterator>::type
-  make_filter_iterator(BaseIterator first, BaseIterator last, const Predicate& p = Predicate());
-}
-
- -
- -

The Filter Iterator Type -Generator

- -The class filter_iterator_generator is a helper class whose -purpose is to construct a filter iterator type. The template -parameters for this class are the Predicate function object -type and the BaseIterator type that is being wrapped. In -most cases the associated types for the wrapped iterator can be -deduced from std::iterator_traits, but in some situations the -user may want to override these types, so there are also template -parameters for each of the iterator's associated types. - -
-template <class Predicate, class BaseIterator,
-          class Value, class Reference, class Pointer, class Category, class Distance>
-class filter_iterator_generator
-{
-public:
-  typedef iterator_adaptor<...> type; // the resulting filter iterator type 
-}
-
- - -

Example

- -The following example uses filter iterator to print out all the -positive integers in an array. - -
-struct is_positive_number {
-  bool operator()(int x) { return 0 < x; }
-};
-int main() {
-  int numbers[] = { 0, -1, 4, -3, 5, 8, -2 };
-  const int N = sizeof(numbers)/sizeof(int);
-
-  typedef boost::filter_iterator_generator<is_positive_number, int*, int>::type FilterIter;
-  is_positive_number predicate;
-  FilterIter::policies_type policies(predicate, numbers + N);
-  FilterIter filter_iter_first(numbers, policies);
-  FilterIter filter_iter_last(numbers + N, policies);
-
-  std::copy(filter_iter_first, filter_iter_last, std::ostream_iterator<int>(std::cout, " "));
-  std::cout << std::endl;
-  return 0;
-}
-
-The output is: -
-4 5 8
-
- - -

Template Parameters

- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
ParameterDescription
PredicateThe function object that determines which elements are retained and which elements are skipped. -
BaseIteratorThe iterator type being wrapped. This type must at least be a model - of the InputIterator concept.
ValueThe value_type of the resulting iterator, -unless const. If const, a conforming compiler strips constness for the -value_type. Typically the default for this parameter is the -appropriate type[1].
Default: -std::iterator_traits<BaseIterator>::value_type
ReferenceThe reference type of the resulting iterator, and in -particular, the result type of operator*(). Typically the default for -this parameter is the appropriate type.
Default: If -Value is supplied, Value& is used. Otherwise -std::iterator_traits<BaseIterator>::reference is -used.
PointerThe pointer type of the resulting iterator, and in - particular, the result type of operator->(). - Typically the default for -this parameter is the appropriate type.
-Default: If Value was supplied, then Value*, -otherwise std::iterator_traits<BaseIterator>::pointer.
CategoryThe iterator_category type for the resulting iterator. -Typically the -default for this parameter is the appropriate type. If you override -this parameter, do not use bidirectional_iterator_tag -because filter iterators can not go in reverse.
-Default: std::iterator_traits<BaseIterator>::iterator_category
DistanceThe difference_type for the resulting iterator. Typically the default for -this parameter is the appropriate type.
-Default: std::iterator_traits<BaseIterator>::difference_type
- - -

Model of

- -The filter iterator adaptor (the type -filter_iterator_generator<...>::type) may be a model of InputIterator or ForwardIterator -depending on the adapted iterator type. - - -

Members

- -The filter iterator type implements all of the member functions and -operators required of the ForwardIterator -concept. In addition it has the following constructor: - -
filter_iterator_generator::type(const BaseIterator& it, const Policies& p = Policies())
- -

-The policies type has only one public function, which is its constructor: - -

filter_iterator_generator::policies_type(const Predicate& p, const BaseIterator& end)
- -

-


-

- -

The Make Filter Iterator Function

- -
-template <class Predicate, class BaseIterator>
-typename filter_generator<Predicate, BaseIterator>::type
-make_filter_iterator(BaseIterator first, BaseIterator last, const Predicate& p = Predicate())
-
- -This function provides a convenient way to create filter iterators. - -

Example

- -In this example we print out all numbers in the array that are -greater than negative two. - -
-int main()
-{
-  int numbers[] = { 0, -1, 4, -3, 5, 8, -2 };
-  const int N = sizeof(numbers)/sizeof(int);
-
-  std::copy(boost::make_filter_iterator(numbers, numbers + N, 
-					std::bind2nd(std::greater(), -2)),
-	    boost::make_filter_iterator(numbers + N, numbers + N, 
-					std::bind2nd(std::greater(), -2)),
-	    std::ostream_iterator(std::cout, " "));
-  std::cout << std::endl;
-
-}
-
-The output is: -
-0 -1 4 5 8 
-
- -

-In the next example we print the positive numbers using the -make_filter_iterator() function. - -

-struct is_positive_number {
-  bool operator()(int x) { return 0 < x; }
-};
-int main()
-{
-  int numbers[] = { 0, -1, 4, -3, 5, 8, -2 };
-  const int N = sizeof(numbers)/sizeof(int);
-
-  std::copy(boost::make_filter_iterator<is_positive_number>(numbers, numbers + N),
-	    boost::make_filter_iterator<is_positive_number>(numbers + N, numbers + N),
-	    std::ostream_iterator<int>(std::cout, " "));
-  std::cout << std::endl;
-  return 0;
-}
-
-The output is: -
-4 5 8
-
- - -

Notes

- -[1] If the compiler does not support partial -specialization and the wrapped iterator type is a builtin pointer then -the Value type must be explicitly specified (don't use the -default). - - -
-

Revised 09 Mar 2001

-

© Copyright Jeremy Siek 2000. Permission to copy, use, -modify, sell and distribute this document is granted provided this copyright -notice appears in all copies. This document is provided "as is" -without express or implied warranty, and with no claim as to its suitability for -any purpose.

- - - - diff --git a/function_output_iterator.htm b/function_output_iterator.htm deleted file mode 100644 index 6061a7b..0000000 --- a/function_output_iterator.htm +++ /dev/null @@ -1,169 +0,0 @@ - - - - - - - - - - Function Output Iterator Adaptor Documentation - - - - - c++boost.gif (8819 bytes) - -

Function Output Iterator Adaptor

- Defined in header boost/function_output_iterator.hpp - -

The function output iterator adaptor makes it easier to create - custom output iterators. The adaptor takes a Unary - Function and creates a model of Output - Iterator. Each item assigned to the output iterator is passed - as an argument to the unary function. The motivation for this - iterator is that creating a C++ Standard conforming output - iterator is non-trivial, particularly because the proper - implementation usually requires a proxy object. On the other hand, - creating a function (or function object) is much simpler. - -

Synopsis

- -
-
-namespace boost {
-  template <class UnaryFunction>
-  class function_output_iterator;
-
-  template <class UnaryFunction>
-  function_output_iterator<UnaryFunction>
-  make_function_output_iterator(const UnaryFunction& f = UnaryFunction())
-}
-
-
- -

Example

- - In this example we create an output iterator that appends - each item onto the end of a string, using the string_appender - function. - -
-
-#include <iostream>
-#include <string>
-#include <vector>
-
-#include <boost/function_output_iterator.hpp>
-
-struct string_appender {
-  string_appender(std::string& s) : m_str(s) { }
-  void operator()(const std::string& x) const {
-    m_str += x;
-  }
-  std::string& m_str;
-};
-
-int main(int, char*[])
-{
-  std::vector<std::string> x;
-  x.push_back("hello");
-  x.push_back(" ");
-  x.push_back("world");
-  x.push_back("!");
-
-  std::string s = "";
-  std::copy(x.begin(), x.end(), 
-            boost::make_function_output_iterator(string_appender(s)));
-  
-  std::cout << s << std::endl;
-
-  return 0;
-}
-
-
- -
- -

The Function Output Iterator Class

- -
-
-template <class UnaryFunction>
-class function_output_iterator;
-
-
- - The function_output_iterator class creates an Output - Iterator out of a - Unary - Function. Each item assigned to the output iterator is passed - as an argument to the unary function. - -

Template Parameters

- - - - - -
Parameter - - Description - -
UnaryFunction - - The function type being wrapped. The return type of the - function is not used, so it can be void. The - function must be a model of Unary - Function.
- -

Concept Model

- The function output iterator class is a model of Output - Iterator. - -

Members

- The function output iterator implements the member functions - and operators required of the Output - Iterator concept. In addition it has the following constructor: -
-explicit function_output_iterator(const UnaryFunction& f = UnaryFunction())
-
-
-
- -
-

The Function Output Iterator Object - Generator

- - The make_function_output_iterator() function provides a - more convenient way to create function output iterator objects. The - function saves the user the trouble of explicitly writing out the - iterator types. If the default argument is used, the function - type must be provided as an explicit template argument. - -
-
-template <class UnaryFunction>
-function_output_iterator<UnaryFunction>
-make_function_output_iterator(const UnaryFunction& f = UnaryFunction())
-
-
- -
- -

© Copyright Jeremy Siek 2001. Permission to copy, use, - modify, sell and distribute this document is granted provided this - copyright notice appears in all copies. This document is provided - "as is" without express or implied warranty, and with no claim as - to its suitability for any purpose. - - - diff --git a/indirect_iterator.htm b/indirect_iterator.htm deleted file mode 100644 index a318424..0000000 --- a/indirect_iterator.htm +++ /dev/null @@ -1,444 +0,0 @@ - - - - - - - - - - Indirect Iterator Adaptor Documentation - - - - - c++boost.gif (8819 bytes) - -

Indirect Iterator Adaptor

- Defined in header boost/iterator_adaptors.hpp - -

The indirect iterator adaptor augments an iterator by applying an - extra dereference inside of operator*(). For example, this - iterator makes it possible to view a container of pointers or - smart-pointers (e.g. std::list<boost::shared_ptr<foo> - >) as if it were a container of the pointed-to type. The following - pseudo-code shows the basic idea of the indirect iterator: - -

-
-// inside a hypothetical indirect_iterator class...
-typedef std::iterator_traits<BaseIterator>::value_type Pointer;
-typedef std::iterator_traits<Pointer>::reference reference;
-
-reference indirect_iterator::operator*() const {
-  return **this->base_iterator;
-}
-
-
- -

Synopsis

- -
-
-namespace boost {
-  template <class BaseIterator,
-            class Value, class Reference, class Category, class Pointer>
-  struct indirect_iterator_generator;
-  
-  template <class BaseIterator,
-            class Value, class Reference, class ConstReference, 
-            class Category, class Pointer, class ConstPointer>
-  struct indirect_iterator_pair_generator;
-
-  template <class BaseIterator>
-  typename indirect_iterator_generator<BaseIterator>::type
-  make_indirect_iterator(BaseIterator base)  
-}
-
-
-
- -

The Indirect Iterator Type - Generator

- The indirect_iterator_generator template is a generator of - indirect iterator types. The main template parameter for this class is the - BaseIterator type that is being wrapped. In most cases the type of - the elements being pointed to can be deduced using - std::iterator_traits, but in some situations the user may want to - override this type, so there are also template parameters that allow a user - to control the value_type, pointer, and - reference types of the resulting iterators. - -
-
-template <class BaseIterator,
-          class Value, class Reference, class Pointer>
-class indirect_iterator_generator
-{
-public:
-  typedef iterator_adaptor<...> type; // the resulting indirect iterator type 
-};
-
-
- -

Example

- This example uses the indirect_iterator_generator to create - indirect iterators which dereference the pointers stored in the - pointers_to_chars array to access the chars in the - characters array. - -
-
-#include <boost/config.hpp>
-#include <vector>
-#include <iostream>
-#include <iterator>
-#include <boost/iterator_adaptors.hpp>
-
-int main(int, char*[])
-{
-  char characters[] = "abcdefg";
-  const int N = sizeof(characters)/sizeof(char) - 1; // -1 since characters has a null char
-  char* pointers_to_chars[N];                        // at the end.
-  for (int i = 0; i < N; ++i)
-    pointers_to_chars[i] = &characters[i];
-  
-  boost::indirect_iterator_generator<char**, char>::type 
-    indirect_first(pointers_to_chars), indirect_last(pointers_to_chars + N);
-
-  std::copy(indirect_first, indirect_last, std::ostream_iterator<char>(std::cout, ","));
-  std::cout << std::endl;
-  
-  // to be continued...
-
-
- -

Template Parameters

- - - - - - - - -
Parameter - - Description - -
BaseIterator - - The iterator type being wrapped. The value_type - of the base iterator should itself be dereferenceable. - The return type of the operator* for the - value_type should match the Reference type. - -
Value - - The value_type of the resulting iterator, unless const. If - Value is const X, a conforming compiler makes the - value_type non-const X[1]. Note that if the default - is used for Value, then there must be a valid specialization - of iterator_traits for the value type of the base iterator. -
- Default: std::iterator_traits<
-   std::iterator_traits<BaseIterator>::value_type - >::value_type
[2] - -
Reference - - The reference type of the resulting iterator, and in - particular, the result type of operator*().
- Default: Value& - -
Pointer - - The pointer type of the resulting iterator, and in - particular, the result type of operator->().
- Default: Value* - -
Category - The iterator_category type for the resulting iterator.
- Default: - std::iterator_traits<BaseIterator>::iterator_category - -
- -

Concept Model

- The indirect iterator will model whichever standard iterator - concept category is modeled by the base iterator. Thus, if the - base iterator is a model of Random - Access Iterator then so is the resulting indirect iterator. If - the base iterator models a more restrictive concept, the resulting - indirect iterator will model the same concept [3]. - -

Members

- The indirect iterator type implements the member functions and operators - required of the Random Access - Iterator concept. In addition it has the following constructor: -
-explicit indirect_iterator_generator::type(const BaseIterator& it)
-
-
-
- -
- -

- -

The Indirect Iterator Pair - Generator

- Sometimes a pair of const/non-const pair of iterators is - needed, such as when implementing a container. The - indirect_iterator_pair_generator class makes it more convenient to - create this pair of iterator types. - -
-
-  template <class BaseIterator,
-            class Value, class Reference, class ConstReference, 
-            class Category, class Pointer, class ConstPointer>
-  struct indirect_iterator_pair_generator;
-{
-public:
-  typedef iterator_adaptor<...> iterator;       // the mutable indirect iterator type 
-  typedef iterator_adaptor<...> const_iterator; // the immutable indirect iterator type 
-};
-
-
- -

Example

- -
-
-  // continuing from the last example...
-
-  typedef boost::indirect_iterator_pair_generator<char**,
-    char, char*, char&, const char*, const char&> PairGen;
-
-  char mutable_characters[N];
-  char* pointers_to_mutable_chars[N];
-  for (int i = 0; i < N; ++i)
-    pointers_to_mutable_chars[i] = &mutable_characters[i];
-
-  PairGen::iterator mutable_indirect_first(pointers_to_mutable_chars),
-    mutable_indirect_last(pointers_to_mutable_chars + N);
-  PairGen::const_iterator const_indirect_first(pointers_to_chars),
-    const_indirect_last(pointers_to_chars + N);
-
-  std::transform(const_indirect_first, const_indirect_last,
-     mutable_indirect_first, std::bind1st(std::plus<char>(), 1));
-
-  std::copy(mutable_indirect_first, mutable_indirect_last,
-      std::ostream_iterator<char>(std::cout, ","));
-  std::cout << std::endl;
-  // to be continued...
-
-
- -

The output is: - -

-
-b,c,d,e,f,g,h,
-
-
- -

Template Parameters

- - - - - - - - - - -
Parameter - - Description - -
BaseIterator - - The iterator type being wrapped. The value_type of the - base iterator should itself be dereferenceable. - The return type of the operator* for the - value_type should match the Reference type. - -
Value - - The value_type of the resulting iterators. - If Value is const X, a conforming compiler makes the - value_type non-const X[1]. Note that if the default - is used for Value, then there must be a valid - specialization of iterator_traits for the value type - of the base iterator.
- - Default: std::iterator_traits<
-   std::iterator_traits<BaseIterator>::value_type - >::value_type
[2] - -
Reference - - The reference type of the resulting iterator, and - in particular, the result type of its operator*().
- Default: Value& - -
ConstReference - - The reference type of the resulting - const_iterator, and in particular, the result type of its - operator*().
- Default: const Value& - -
Category - The iterator_category type for the resulting iterator.
- Default: - std::iterator_traits<BaseIterator>::iterator_category - -
Pointer - - The pointer type of the resulting iterator, and - in particular, the result type of its operator->().
- Default: Value* - -
ConstPointer - - The pointer type of the resulting const_iterator, - and in particular, the result type of its operator->().
- Default: const Value* - -
- -

Concept Model

- - The indirect iterators will model whichever standard iterator - concept category is modeled by the base iterator. Thus, if the - base iterator is a model of Random - Access Iterator then so are the resulting indirect - iterators. If the base iterator models a more restrictive concept, - the resulting indirect iterators will model the same concept [3]. - - -

Members

- The resulting iterator and const_iterator types implement - the member functions and operators required of the Random Access - Iterator concept. In addition they support the following constructors: - -
-
-explicit indirect_iterator_pair_generator::iterator(const BaseIterator& it)
-explicit indirect_iterator_pair_generator::const_iterator(const BaseIterator& it)
-
-
-
-
- -
- -

- -

The Indirect Iterator Object - Generator

- The make_indirect_iterator() function provides a more convenient - way to create indirect iterator objects. The function saves the user the - trouble of explicitly writing out the iterator types. - -
-
-template <class BaseIterator>
-typename indirect_iterator_generator<BaseIterator>::type
-make_indirect_iterator(BaseIterator base)  
-
-
- -

Example

- Here we again print the chars from the array characters - by accessing them through the array of pointers pointer_to_chars, - but this time we use the make_indirect_iterator() function which - saves us some typing. - -
-
-  // continuing from the last example...
-
-  std::copy(boost::make_indirect_iterator(pointers_to_chars), 
-      boost::make_indirect_iterator(pointers_to_chars + N),
-      std::ostream_iterator<char>(std::cout, ","));
-  std::cout << std::endl;
-
-  return 0;
-}
-
-
- The output is: - -
-
-a,b,c,d,e,f,g,
-
-
-
- -

Notes

- -

- -

[2] If your compiler does not support partial - specialization and the base iterator or its value_type is a - builtin pointer type, you will not be able to use the default for - Value and will need to specify this type explicitly. - -

[3]There is a caveat to which concept the - indirect iterator can model. If the return type of the - operator* for the base iterator's value type is not a - true reference, then strickly speaking, the indirect iterator can - not be a model of Forward - Iterator or any of the concepts that refine it. In this case - the Category for the indirect iterator should be - specified as std::input_iterator_tag. However, even in - this case, if the base iterator is a random access iterator, the - resulting indirect iterator will still satisfy most of the - requirements for Random - Access Iterator. - -


- -

Revised - 18 Sep 2001 - - -

© Copyright Jeremy Siek and David Abrahams 2001. Permission to - copy, use, modify, sell and distribute this document is granted provided - this copyright notice appears in all copies. This document is provided "as - is" without express or implied warranty, and with no claim as to its - suitability for any purpose. - - - - - - - - diff --git a/iterator_adaptors.htm b/iterator_adaptors.htm deleted file mode 100644 index c3d249e..0000000 --- a/iterator_adaptors.htm +++ /dev/null @@ -1,1000 +0,0 @@ - - - - - - - - - - Boost Iterator Adaptor Library - - - - - c++boost.gif (8819 bytes) - -

Boost Iterator Adaptor Library

- -

Introduction

- -

The Iterator Adaptor library allows you transform an arbitrary ``base'' - type into a standard-conforming iterator with the behaviors you choose. - Doing so is especially easy if the ``base'' type is itself an iterator. The - library also supplies several example adaptors which apply - specific useful behaviors to arbitrary base iterators. - -

Backward Compatibility Note

- -

The library's interface has changed since it was first released, breaking - backward compatibility: - -

    - -
  1. Policies classes now operate on instances of the - whole iterator_adaptor object, rather than just operating on the - Base object. This change not only gives the policies class access - to both members of a pair of interacting iterators, but also eliminates the - need for the ugly type<Reference> and - type<Difference> parameters to various policy functions. - -
  2. The Named Template Parameter - interface has been made simpler, easier to use, and compatible with more - compilers. - -
- -

Other Documentation

- -

``Policy Adaptors and the Boost Iterator - Adaptor Library'' is a technical paper describing this library and the - powerful design pattern on which it is based. It was presented at the C++ Template Workshop at OOPSLA - 2001; the slides from the talk are available here. Please note that while the slides - incorporate the minor interface changes described in the previous section, - the paper does not. - -

Table of Contents

- - - -

Dave - Abrahams started the library, applying policy class technique and - handling const/non-const iterator interactions. He also contributed the - indirect_ and reverse_ iterator generators, and expanded - counting_iterator_generator to - cover all incrementable types. He edited most of the documentation, - sometimes heavily.
- Jeremy - Siek contributed the transform - iterator adaptor, the integer-only version of counting_iterator_generator, - the function output iterator - adaptor, and most of the documentation.
- John - Potter contributed the projection_ and filter_ iterator generators and made some - simplifications to the main iterator_adaptor template.
- Jens Maurer - contributed the generator iterator - adaptor.
- Toon Knapen contributed the permutation - iterator adaptor.
- Ronald Garcia - contributed the shared container iterator - adaptor.
- -

Class template - iterator_adaptor

- Implementing standard conforming iterators is a non-trivial task. There are - some fine points such as the interactions between an iterator and its - corresponding const_iterator, and there are myriad operators that should be - implemented but are easily forgotten or mishandled, such as - operator->(). Using iterator_adaptor, you can easily - implement an iterator class, and even more easily extend and adapt existing iterator - types. Moreover, it is easy to make a pair of interoperable const - and non-const iterators. - -

iterator_adaptor is declared like this: -

-template <class Base, class Policies, 
-    class ValueOrNamedParam = typename std::iterator_traits<Base>::value_type,
-    class ReferenceOrNamedParam = ...(see below),
-    class PointerOrNamedParam = ...(see below),
-    class CategoryOrNamedParam = typename std::iterator_traits<Base>::iterator_category,
-    class DistanceOrNamedParam = typename std::iterator_traits<Base>::difference_type>
-struct iterator_adaptor;
-
- -

Template Parameters

- -

Although iterator_adaptor takes seven template parameters, - defaults have been carefully chosen to minimize the number of parameters - you must supply in most cases, especially if Base is an - iterator. - - - - - - - - - - - -
Parameter - - Description - - Requirements - -
Base - - The data type on which the resulting iterator is based. Do - not be misled by the name "Base": this is not a base - class. - - - Assignable, - Default Constructible - -
Policies - - A policy - class that supplies core functionality to the resulting iterator. - - See table below. - -
Value - - The value_type of the resulting iterator, unless const. If - Value is const X the - value_type will be (non-const) X[1]. If the value_type you wish to use is an abstract - base class see note [5].
- Default: - std::iterator_traits<Base>::value_type [2] - -
Reference - - The reference type of the resulting iterator, and in - particular, the result type of operator*().
- Default: If Value is supplied, Value& is - used. Otherwise - std::iterator_traits<Base>::reference is used. [7] - -
ForwardIterators, - BidirectionalIterators, - and RandomAccessIterators - require that Reference is a true reference type (e.g. not a proxy). - -
Pointer - - The pointer type of the resulting iterator, and in - particular, the result type of operator->().
- Default: If Value was not supplied, std::iterator_traits<Base>::pointer. [7] Otherwise, if iterator_category is - input_iterator, then a class yielding - Value* when operator->() is applied. - Otherwise, Value*. - -
value_type* or a - class which yields value_type* when - operator->() is applied. - -
Category - - The iterator_category type for the resulting iterator.
- Default: - std::iterator_traits<Base>::iterator_category - -
One of - std::input_iterator_tag, - std::output_iterator_tag, - std::forward_iterator_tag, - std::bidirectional_iterator_tag, or - std::random_access_iterator_tag. - -
Distance - - The difference_type for the resulting iterator.
- Default: - std::iterator_traits<Base>::difference_type -
A signed integral type - -
NamedParam - - A named template parameter (see below). -
- -

Named Template Parameters

- - With seven template parameters, providing arguments for - iterator_adaptor in the correct order can be challenging. - Also, often times one would like to specify the sixth or seventh - template parameter, but use the defaults for the third through - fifth. As a solution to these problems we provide a mechanism for - naming the last five template parameters, and providing them in - any order through a set of named template parameters. The following - classes are provided for specifying the parameters. Any of these - classes can be used for any of the last five template parameters - of iterator_adaptor. -
-
-template <class Value> struct value_type_is;
-template <class Reference> struct reference_is;
-template <class Pointer> struct pointer_is;
-template <class Distance> struct difference_type_is;
-template <class Category> struct iterator_category_is;
-
-
- - For example, the following adapts foo_iterator to create - an InputIterator - with reference type foo, and whose other traits - are determined according to the defaults described above. - -
-
-typedef iterator_adaptor<foo_iterator, foo_policies,
-  reference_is<foo>, iterator_category_is<std::input_iterator_tag>
-  > MyIterator;
-
-
- - -

The Policies Class

- -

The main task in using iterator_adaptor is creating an - appropriate Policies class. The Policies class will become - the functional heart of the resulting iterator, supplying the core - operations that determine its behavior. The iterator_adaptor - template defines all of the operators required of a Random Access - Iterator by dispatching to a Policies object. Your - Policies class must implement a subset of the core iterator - operations below corresponding to the iterator categories you want it to - support.
-
- - - - - - - - - - - - - -
- Policies Class Requirements
- T: adapted iterator type; x, y: objects of type - T; p: T::policies_type - d: - T::difference_type; i1, i2: - T::base_type -
Expression - - Effects - - Implements Operations - - Required for Iterator Categories - -
p.initialize(b) - - optionally modify base iterator during iterator construction - - constructors - - Input/ Output/ Forward/ Bidirectional/ - Random Access - - -
p.dereference(x) - - returns an element of the iterator's reference type - - *x, x[d] - - -
p.equal(x, y) - - tests the iterator for equality - - i1 == i2, i1 != i2 - -
p.increment(x) - - increments the iterator - - ++x, x++ - -
p.decrement(x) - - decrements the iterator - - --x, x-- - - Bidirectional/ - Random Access - -
p.distance(x, y) - - measures the distance between iterators - - y - x, x < y - - Random - Access - -
p.advance(x, n) - - adds an integer offset to iterators - - -x + d, -d + x, - -
-x += d, -x - d,
-x -= d - -
- -

The library also supplies a "trivial" policy class, - default_iterator_policies, which implements all seven of the core - operations in the usual way. If you wish to create an iterator adaptor that - only changes a few of the base type's behaviors, then you can derive your - new policy class from default_iterator_policies to avoid retyping - the usual behaviors. You should also look at - default_iterator_policies as the ``boilerplate'' for your own - policy classes, defining functions with the same interface. This is the - definition of default_iterator_policies:
-
- -

-
-struct default_iterator_policies
-{
-    // Some of these members were defined static, but Borland got confused
-    // and thought they were non-const. Also, Sun C++ does not like static
-    // function templates.
-
-    template <class Base>
-    void initialize(Base&)
-        { }
-
-    template <class IteratorAdaptor>
-    typename IteratorAdaptor::reference dereference(const IteratorAdaptor& x) const
-        { return *x.base(); }
-
-    template <class IteratorAdaptor>
-    void increment(IteratorAdaptor& x)
-        { ++x.base(); }
-
-    template <class IteratorAdaptor>
-    void decrement(IteratorAdaptor& x)
-        { --x.base(); }
-
-    template <class IteratorAdaptor, class DifferenceType>
-    void advance(IteratorAdaptor& x, DifferenceType n)
-        { x.base() += n; }
-
-    template <class IteratorAdaptor1, class IteratorAdaptor2>
-    typename IteratorAdaptor1::difference_type
-    distance(const IteratorAdaptor1& x, const IteratorAdaptor2& y) const
-        { return y.base() - x.base(); }
-
-    template <class IteratorAdaptor1, class IteratorAdaptor2>
-    bool equal(const IteratorAdaptor1& x, const IteratorAdaptor2& y) const
-        { return x.base() == y.base(); }
-};
-
- -

Template member functions are used throughout - default_iterator_policies so that it can be employed with a wide - range of iterators. If we had used concrete types above, we'd have tied the - usefulness of default_iterator_policies to a particular range of - adapted iterators. If you follow the same pattern with your - Policies classes, you can use them to generate more specialized - adaptors along the lines of those supplied by this library. - -

Additional Members

- In addition to all of the member functions required of a Random Access - Iterator, the iterator_adaptor class template defines the - following members.
-
- - - - - - - -
explicit iterator_adaptor(const Base&, const Policies& = - Policies()) -

- Construct an adapted iterator from a base object and a policies - object. As this constructor is explicit, it does not - provide for implicit conversions from the Base type to - the iterator adaptor. - -
template <class B, class V, class R, class P>
- iterator_adaptor(const - iterator_adaptor<B,Policies,V,R,P,Category,Distance>&)
-

- This constructor allows for conversion from mutable to - constant adapted iterators. See below for more details.
- Requires: B is convertible to Base. - -
const base_type& base() const; -

- Return a const reference to the base object. - -
base_type& base(); -

- Return a reference to the base object. This is to give the policies object - access to the base object. See above for policies - iterator_adaptor interaction.[8] - -
const Policies& policies() const; -

- Return a const reference to the policies object. - -
Policies& policies(); -

- Return a reference to the policies object. -
- -

Example

- -

It is often useful to automatically apply some function to the value - returned by dereferencing an iterator. The transform iterator makes it easy to create - an iterator adaptor which does just that. Here we will show how easy it is - to implement the transform iterator using the iterator_adaptor - template. - -

We want to be able to adapt a range of iterators and functions, so the - policies class will have a template parameter for the function type and it - will have a data member of that type. We know that the function takes one - argument and that we'll need to be able to deduce the result_type - of the function so we can use it for the adapted iterator's - value_type. AdaptableUnaryFunction - is the Concept - that fulfills those requirements. - -

To implement a transform iterator we will only change one of the base - iterator's behaviors, so the transform_iterator_policies class can - inherit the rest from default_iterator_policies. We will define the - dereference() member function, which is used to implement - operator*() of the adapted iterator. The implementation will - dereference the base iterator and apply the function object. The complete - code for transform_iterator_policies is:
-
- -

-template <class AdaptableUnaryFunction>
-struct transform_iterator_policies : public default_iterator_policies
-{
-    transform_iterator_policies() { }
-
-    transform_iterator_policies(const AdaptableUnaryFunction& f)
-        : m_f(f) { }
-    
-    template <class IteratorAdaptor>
-    typename IteratorAdaptor::reference
-    dereference(const IteratorAdaptor& iter) const
-        { return m_f(*iter.base()); }
-
-    AdaptableUnaryFunction m_f;
-};
-
-
- -

The next step is to use the iterator_adaptor template to - construct the transform iterator type. The nicest way to package the - construction of the transform iterator is to create a type generator. - The first template parameter to the generator will be the type of the - function object and the second will be the base iterator type. We use - iterator_adaptor to define the transform iterator type as a nested - typedef inside the transform_iterator_generator class. - Because the function may return by-value, we must limit the - iterator_category to Input Iterator, and - the iterator's reference type cannot be a true reference (the - standard allows this for input iterators), so in this case we can use few - of iterator_adaptor's default template arguments.
-
- - -

-
-template <class AdaptableUnaryFunction, class Iterator>
-struct transform_iterator_generator
-{
-    typedef typename AdaptableUnaryFunction::result_type value_type;
-public:
-    typedef iterator_adaptor<Iterator, 
-        transform_iterator_policies<AdaptableUnaryFunction>,
-        value_type, value_type, value_type*, std::input_iterator_tag>
-      type;
-};
-
-
- -

As a finishing touch, we will create an object generator - for the transform iterator. Our object generator makes it more - convenient to create a transform iterator.
-
- - -

-
-template <class AdaptableUnaryFunction, class Iterator>
-typename transform_iterator_generator<AdaptableUnaryFunction,Iterator>::type
-make_transform_iterator(Iterator base,
-                        const AdaptableUnaryFunction& f = AdaptableUnaryFunction())
-{
-    typedef typename transform_iterator_generator<AdaptableUnaryFunction,
-      Iterator>::type result_t;
-    return result_t(base, f);
-}
-
-
- -

Here is an example that shows how to use a transform iterator to iterate - through a range of numbers, multiplying each of them by 2 and printing the - result to standard output.
-
- - -

-
-#include <functional>
-#include <algorithm>
-#include <iostream>
-#include <boost/iterator_adaptors.hpp>
-
-int main(int, char*[])
-{
-  int x[] = { 1, 2, 3, 4, 5, 6, 7, 8 };
-  const int N = sizeof(x)/sizeof(int);
-  std::cout << "multiplying the array by 2:" << std::endl;
-  std::copy(boost::make_transform_iterator(x, std::bind1st(std::multiplies<int>(), 2)),
-      boost::make_transform_iterator(x + N, std::bind1st(std::multiplies<int>(), 2)),
-      std::ostream_iterator<int>(std::cout, " "));
-  std::cout << std::endl;
-  return 0;
-}
-
- This output is: -
-2 4 6 8 10 12 14 16
-
-
- -

Iterator Interactions

- -

C++ allows const and non-const pointers to interact in - the following intuitive ways: - -

- - Getting user-defined iterators to work together that way is nontrivial (see - here for an example of where - the C++ standard got it wrong), but iterator_adaptor can make it - easy. The rules are as follows: - - - -

Example

- -

The Projection Iterator adaptor is similar to the transform iterator adaptor in that -its operator*() applies some function to the result of -dereferencing the base iterator and then returns the result. The -difference is that the function must return a reference to some -existing object (for example, a data member within the -value_type of the base iterator). - -

-The projection_iterator_pair_generator template - is a special two-type generator for mutable and constant versions of a - projection iterator. It is defined as follows: -

-
-template <class AdaptableUnaryFunction, class Iterator, class ConstIterator>
-struct projection_iterator_pair_generator {
-    typedef typename AdaptableUnaryFunction::result_type value_type;
-    typedef projection_iterator_policies<AdaptableUnaryFunction> policies;
-public:
-    typedef iterator_adaptor<Iterator,policies,value_type> iterator;
-    typedef iterator_adaptor<ConstIterator,policies,value_type,
-        const value_type&,const value_type*> const_iterator;
-};
-
-
- -

It is assumed that the Iterator and ConstIterator arguments are corresponding mutable -and constant iterators.

- -

Challenge

- -

There is an unlimited number of ways the iterator_adaptors - class can be used to create iterators. One interesting exercise would be to - re-implement the iterators of std::list and slist - using iterator_adaptors, where the adapted Iterator types - would be node pointers. - -

Concept Model

- Depending on the Base and Policies template parameters, - an iterator_adaptor can be a Input Iterator, Forward - Iterator, Bidirectional - Iterator, or Random Access - Iterator. - -

Declaration Synopsis

-
-template <class Base, class Policies, 
-    class Value = typename std::iterator_traits<Base>::value_type,
-    class Reference = ...(see below),
-    class Pointer = ...(see below),
-    class Category = typename std::iterator_traits<Base>::iterator_category,
-    class Distance = typename std::iterator_traits<Base>::difference_type
-         >
-struct iterator_adaptor
-{
-    typedef Distance difference_type;
-    typedef typename boost::remove_const<Value>::type value_type;
-    typedef Pointer pointer;
-    typedef Reference reference;
-    typedef Category iterator_category;
-    typedef Base base_type;
-    typedef Policies policies_type;
-
-    iterator_adaptor();
-    explicit iterator_adaptor(const Base&, const Policies& = Policies());
-
-    base_type&       base();
-    const base_type& base() const;
-
-    template <class B, class V, class R, class P>
-    iterator_adaptor(
-        const iterator_adaptor<B,Policies,V,R,P,Category,Distance>&);
-
-    reference operator*() const; [6]
-    operator_arrow_result_type operator->() const; [3]
-    value_type operator[](difference_type n) const; [4], [6]
-
-    iterator_adaptor& operator++();
-    iterator_adaptor& operator++(int);
-    iterator_adaptor& operator--();
-    iterator_adaptor& operator--(int);
-
-    iterator_adaptor& operator+=(difference_type n);
-    iterator_adaptor& operator-=(difference_type n);
-
-    iterator_adaptor& operator-(Distance x) const;
-};
-
-template <class B, class P, class V, class R, class Ptr, 
-    class C, class D1, class D2>
-iterator_adaptor<B,P,V,R,Ptr,C,D1>
-operator+(iterator_adaptor<B,P,V,R,Ptr,C,D1>, D2);
-
-template <class B, class P, class V, class R, class Ptr,
-    class C, class D1, class D2>
-iterator_adaptor<B,P,V,R,P,C,D1>
-operator+(D2, iterator_adaptor<B,P,V,R,Ptr,C,D1> p);
-
-template <class B1, class B2, class P, class V1, class V2,
-    class R1, class R2, class P1, class P2, class C, class D>
-Distance operator-(const iterator_adaptor<B1,P,V1,R1,P1,C,D>&, 
-                   const iterator_adaptor<B2,P,V2,R2,P2,C,D>&);
-
-template <class B1, class B2, class P, class V1, class V2,
-    class R1, class R2, class P1, class P2, class C, class D>
-bool operator==(const iterator_adaptor<B1,P,V1,R1,P1,C,D>&, 
-                const iterator_adaptor<B2,P,V2,R2,P2,C,D>&);
-
-// and similarly for operators !=, <, <=, >=, >
-
- -

Portability

- -

Generally, the iterator adaptors library can be compiled with all compilers - supporting iterator traits and type traits.

- -

Microsoft VC++ is not able to handle iterator adaptors based on a - vector::iterator without specifying all template paramters explicitly. - In case not all template parameters are specified explicitly, the iterator adaptors - library will deduce these types using iterator_traits. But since in VC++ a - vector::iterator is a T*, VC++ can't handle using - iterator_traits due to the lack of partial template specialization.

- - -

Notes

- -

[1] The standard specifies that the value_type - of const iterators to T (e.g. const T*) is - non-const T, while the pointer and - reference types for all Forward Iterators are - const T* and const T&, respectively. Stripping the - const-ness of Value allows you to easily make a constant - iterator by supplying a const type for Value, and allowing - the defaults for the Pointer and Reference parameters to - take effect. Although compilers that don't support partial specialization - won't strip const for you, having a const value_type is - often harmless in practice. - -

[2] If your compiler does not support partial - specialization and the base iterator is a builtin pointer type, you - will not be able to use the default for Value and will have to - specify this type explicitly. - -

[3] The result type for the operator->() - depends on the category and value type of the iterator and is somewhat - complicated to describe. But be assured, it works in a stardard conforming - fashion, providing access to members of the objects pointed to by the - iterator. - -

[4] The result type of operator[]() is - value_type instead of reference as might be expected. - There are two reasons for this choice. First, the C++ standard only - requires that the return type of an arbitrary Random Access - Iterator's operator[]be ``convertible to T'' (Table 76), so - when adapting an arbitrary base iterator we may not have a reference to - return. Second, and more importantly, for certain kinds of iterators, - returning a reference could cause serious memory problems due to the - reference being bound to a temporary object whose lifetime ends inside of - the operator[]. - -

[5] - The value_type of an iterator may not be - an abstract base class, however many common uses of iterators - never need the value_type, only the reference type. - If you wish to create such an iterator adaptor, use a dummy - type such as char for the Value parameter, - and use a reference to your abstract base class for - the Reference parameter. Note that such an iterator - does not fulfill the C++ standards requirements for a - - Forward Iterator, so you will need to use a less restrictive - iterator category such as std::input_iterator_tag. - -

[6] - There is a common misconception that an iterator should have two - versions of operator* and of operator[], one - version that is a const member function and one version - that is non-const. Perhaps the source of this - misconception is that containers typically have const and - non-const versions of many of their member functions. Iterators, - however, are different. A particular iterator type can be either - mutable or constant (but not both). One can assign - to and change the object pointed to by a mutable iterator whereas a - constant iterator returns constant objects when dereferenced. Whether - the iterator object itself is const has nothing to do with - whether the iterator is mutable or constant. This is analogous to - the way built-in pointer types behave. For example, one can - modify objects pointed to by a const pointer -

-    int* const x = new int;
-    int i = 3;
-    *x = i;
-
- but one cannot modify objects pointed to by a pointer - to const -
-    int const* x = new int;
-    int i = 3;
-    *x = i;
-
- -

[7] - If you are using a compiler that does not have a version of - std::iterator_traits that works for pointers (i.e., if your - compiler does not support partial specialization) then if the - Base type is a const pointer, then the correct defaults - for the reference and pointer types can not be - deduced. You must specify these types explicitly. -

[8] - Exposing the base object might be considered as being dangerous. - A possible fix would require compiler support for template friends. - As this is not widely available today, the base object remains exposed for now. - -


- -

Revised - 30 Nov 2001 - - -

© Copyright Dave Abrahams and Jeremy Siek 2001. Permission to copy, - use, modify, sell and distribute this document is granted provided this - copyright notice appears in all copies. This document is provided "as is" - without express or implied warranty, and with no claim as to its - suitability for any purpose. - - - - - - - - - - - - - - - diff --git a/iterator_adaptors.pdf b/iterator_adaptors.pdf deleted file mode 100644 index 6ae01b0aaf00b2db1ef3cda524c9b0c9c188eec0..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 84856 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 QhF8I1^JdLD^y(P!zfC1?#Q*>R diff --git a/iterator_adaptors.ppt b/iterator_adaptors.ppt deleted file mode 100644 index b90c0aa04512f2320f08ede9d328c5b3f28c5f72..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 103936 zcmeFYX;c$;|2I4{*-3x|0wipP)gS=^VHa`2CLn51N&ykW79#=;h!(AFGYKG@HXf}+)4sI`~a_Ub+3eg5Y>=Xv+Me9rmDkwEgB-|}5Q z-(`$9S*D{G>>mUFuU8~M0RHdWE@}y&1+&^Mv@Awb*+E06+kh zfc^HI^v{pj8*!6(l^6i-6Qb^|Ig0(w%Z*>V3IKL`0Dw{r0KdBfK*db}DB1`Ba|PJ_ zbpYV->8V$UEr3avBq=3U1c_!>(YQg@=unF*wTks1oh_Fj!XaWAgFOjSTz`mCmu@s z&HujsmjeIaC{UHO4pXP3(1aLqO8Fti*in{F$RNP67Vi$E@V1|eaBJT7 b0OfH-6 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 O+kYZ3x+`-s@c%y%_Bt>C diff --git a/permutation_iterator.htm b/permutation_iterator.htm deleted file mode 100644 index ea68387..0000000 --- a/permutation_iterator.htm +++ /dev/null @@ -1,177 +0,0 @@ - - - - -Permutation Iterator Adaptor Documentation - - - - -

Permutation Iterator Adaptor

-

Defined in header boost/permutation_iterator.hpp

-

The permutation iterator adaptor provides an iterator to a permutation of a given range. -(see definition of permutation). -The adaptor takes two arguments -

    -
  • an iterator to the range V on which the permutation will be applied
  • -
  • the reindexing scheme that defines how the elements of V will be permuted.
  • -
- -

Note that the permutation iterator is not limited to strict permutations of the given range V. -The distance between begin and end of the reindexing iterators is allowed to be smaller compared to the -size of the range V, in which case the permutation iterator only provides a permutation of a subrange of V. -The indexes neither need to be unique. In this same context, it must be noted that the past the end permutation iterator is -completely defined by means of the past-the-end iterator to the indices

- -

Synopsis

- -
-
-namespace boost {
-  template <class IndexIterator>
-  class permutation_iterator_policies;
-
-  template <class ElementIterator, class IndexIterator>
-  class permutation_iterator_generator;
-
-  template <class ElementIterator, class IndexIterator>
-  typename permutation_iterator_generator<ElementIterator, IndexIterator>::type
-  make_permutation_iterator(ElementIterator& base, IndexIterator& indexing);
-}
-
-
- - -

The Permutation Iterator Generator Class Template

- -

The permutation_iterator_generator is a helper class whose purpose -is to construct a permutation iterator type. This class has -two template arguments, the first being the iterator type over the range V, the -second being the type of the iterator over the indices. - -

-
-template <class ElementIterator, class IndexIterator>
-class permutation_iterator_generator
-{
-public:
-  typedef iterator_adaptor<...> type; // the resulting permutation iterator type 
-}
-
-
- - -

Template Parameters

- - - - - - - - - - - - - - - -
ParameterDescription
ElementIteratorThe iterator over the elements to be permuted. This type must be a model -of RandomAccessIterator
IndexIteratorThe iterator over the new indexing scheme. This type must at least be a model -of ForwardIterator. -The IndexIterator::value_type must be convertible to the -ElementIterator::difference_type.
- -

Concept Model

-The permutation iterator is always a model of the same concept as the IndexIterator. - -

Members

-The permutation iterator implements the member functions -and operators required for the -Random Access Iterator -concept. However, the permutation iterator can only meet the complexity guarantees -of the same concept as the IndexIterator. Thus for instance, although the permutation -iterator provides operator+=(distance), this operation will take linear time -in case the IndexIterator is a model of ForwardIterator instead of amortized constant time. - -
- -

The Permutation Iterator Object Generator

- -The make_permutation_iterator() function provides a -convenient way to create permutation iterator objects. The function -saves the user the trouble of explicitly writing out the iterator -types. - -
-
-template <class ElementIterator, class IndexIterator >
-typename permutation_iterator_generator<ElementIterator, IndexIterator>::type
-make_permutation_iterator(ElementIterator& base, IndexIterator& indices);
-
-
- -

Example

-
-
-  using namespace boost;
-  int i = 0;
-
-  typedef std::vector< int > element_range_type;
-  typedef std::list< int > index_type;
-
-  static const int element_range_size = 10;
-  static const int index_size = 4;
-
-  element_range_type elements( element_range_size );
-  for(element_range_type::iterator el_it = elements.begin() ; el_it != elements.end() ; ++el_it) *el_it = std::distance(elements.begin(), el_it);
-
-  index_type indices( index_size );
-  for(index_type::iterator i_it = indices.begin() ; i_it != indices.end() ; ++i_it ) *i_it = element_range_size - index_size + std::distance(indices.begin(), i_it);
-  std::reverse( indices.begin(), indices.end() );
-
-  typedef permutation_iterator_generator< element_range_type::iterator, index_type::iterator >::type permutation_type;
-  permutation_type begin = make_permutation_iterator( elements.begin(), indices.begin() );
-  permutation_type it = begin;
-  permutation_type end = make_permutation_iterator( elements.begin(), indices.end() );
-
-  std::cout << "The original range is : ";
-  std::copy( elements.begin(), elements.end(), std::ostream_iterator< int >( std::cout, " " ) );
-  std::cout << "\n";
-
-  std::cout << "The reindexing scheme is : ";
-  std::copy( indices.begin(), indices.end(), std::ostream_iterator< int >( std::cout, " " ) );
-  std::cout << "\n";
-
-  std::cout << "The permutated range is : ";
-  std::copy( begin, end, std::ostream_iterator< int >( std::cout, " " ) );
-  std::cout << "\n";
-
-  std::cout << "Elements at even indices in the permutation : ";
-  it = begin;
-  for(i = 0; i < index_size / 2 ; ++i, it+=2 ) std::cout << *it << " ";
-  std::cout << "\n";
-
-  std::cout << "Permutation backwards : ";
-  it = begin + (index_size);
-  assert( it != begin );
-  for( ; it-- != begin ; ) std::cout << *it << " ";
-  std::cout << "\n";
-
-  std::cout << "Iterate backward with stride 2 : ";
-  it = begin + (index_size - 1);
-  for(i = 0 ; i < index_size / 2 ; ++i, it-=2 ) std::cout << *it << " ";
-  std::cout << "\n";
-
-
- -



-Thanks: The permutation iterator is only a small addition to the superb iterator adaptors -library of David Abrahams and Jeremy Siek. -

- -Copyright 2001 Toon Knapen. - - - diff --git a/projection_iterator.htm b/projection_iterator.htm deleted file mode 100644 index e6b0df3..0000000 --- a/projection_iterator.htm +++ /dev/null @@ -1,391 +0,0 @@ - - - - - - -Projection Iterator Adaptor Documentation - - - - -c++boost.gif (8819 bytes) - -

Projection Iterator Adaptor

- -Defined in header -boost/iterator_adaptors.hpp - -

-The projection iterator adaptor is similar to the transform iterator adaptor in that -its operator*() applies some function to the result of -dereferencing the base iterator and then returns the result. The -difference is that the function must return a reference to some -existing object (for example, a data member within the -value_type of the base iterator). The following -pseudo-code gives the basic idea. The data member p is -the function object. - -

-  reference projection_iterator::operator*() const {
-    return this->p(*this->base_iterator);
-  }
-
- -

Synopsis

- -
-namespace boost {
-  template <class AdaptableUnaryFunction, class BaseIterator>
-  struct projection_iterator_generator;
-  
-  template <class AdaptableUnaryFunction, 
-            class BaseIterator, class ConstBaseIterator>
-  struct projection_iterator_pair_generator;
-
-  template <class AdaptableUnaryFunction, class BaseIterator>
-  typename projection_iterator_generator<AdaptableUnaryFunction, BaseIterator>::type
-  make_projection_iterator(BaseIterator base,
-			   const AdaptableUnaryFunction& p = AdaptableUnaryFunction())
-
-  template <class AdaptableUnaryFunction, class ConstBaseIterator>
-  typename projection_iterator_generator<AdaptableUnaryFunction, ConstBaseIterator>::type
-  make_const_projection_iterator(ConstBaseIterator base,
-                                 const AdaptableUnaryFunction& p = AdaptableUnaryFunction())  
-}
-
- -
- -

The Projection Iterator Type -Generator

- -The class projection_iterator_generator is a helper class -whose purpose is to construct an projection iterator type. The main -template parameter for this class is the AdaptableUnaryFunction -function object type and the BaseIterator type that is being -wrapped. - -
-template <class AdaptableUnaryFunction, class BaseIterator>
-class projection_iterator_generator
-{
-public:
-  typedef iterator_adaptor<...> type; // the resulting projection iterator type 
-};
-
- -

Example

- -In the following example we have a list of personnel records. Each -record has an employee's name and ID number. We want to be able to -traverse through the list accessing either the name or the ID numbers -of the employees using the projection iterator so we create the -function object classes select_name and -select_ID. We then use the -projection_iterator_generator class to create a projection -iterator and use it to print out the names of the employees. - -
-#include <boost/config.hpp>
-#include <list>
-#include <iostream>
-#include <iterator>
-#include <algorithm>
-#include <string>
-#include <boost/iterator_adaptors.hpp>
-
-struct personnel_record {
-  personnel_record(std::string n, int id) : m_name(n), m_ID(id) { }
-  std::string m_name;
-  int m_ID;
-};
-
-struct select_name {
-  typedef personnel_record argument_type;
-  typedef std::string result_type;
-  const std::string& operator()(const personnel_record& r) const {
-    return r.m_name;
-  }
-  std::string& operator()(personnel_record& r) const {
-    return r.m_name;
-  }
-};
-
-struct select_ID {
-  typedef personnel_record argument_type;
-  typedef int result_type;
-  const int& operator()(const personnel_record& r) const {
-    return r.m_ID;
-  }
-  int& operator()(personnel_record& r) const {
-    return r.m_ID;
-  }
-};
-
-int main(int, char*[])
-{
-  std::list<personnel_record> personnel_list;
-
-  personnel_list.push_back(personnel_record("Barney", 13423));
-  personnel_list.push_back(personnel_record("Fred", 12343));
-  personnel_list.push_back(personnel_record("Wilma", 62454));
-  personnel_list.push_back(personnel_record("Betty", 20490));
-
-  // Example of using projection_iterator_generator
-  // to print out the names in the personnel list.
-
-  boost::projection_iterator_generator<select_name,
-    std::list<personnel_record>::iterator>::type
-    personnel_first(personnel_list.begin()),
-    personnel_last(personnel_list.end());
-
-  std::copy(personnel_first, personnel_last,
-            std::ostream_iterator<std::string>(std::cout, "\n"));
-  std::cout << std::endl;
-
-  // to be continued...
-
-The output for this part is: -
-Barney
-Fred
-Wilma
-Betty
-
- -

Template Parameters

- - - - - - - - - - - - - - - - - -
ParameterDescription
AdaptableUnaryFunctionThe type of the function object. The argument_type of the -function must match the value type of the base iterator. The function -should return a reference to the function's result_type. -The result_type will be the resulting iterator's value_type. -
BaseIteratorThe iterator type being wrapped.
- -

Model of

- -If the base iterator is a model of Random -Access Iterator then so is the resulting projection iterator. If -the base iterator supports less functionality than this the resulting -projection iterator will also support less functionality. - -

Members

- -The projection iterator type implements the member functions and -operators required of the Random -Access Iterator concept. -In addition it has the following constructor: - -
-projection_iterator_generator::type(const BaseIterator& it,
-                                    const AdaptableUnaryFunction& p = AdaptableUnaryFunction())
-
- -

-


-

- -

The Projection Iterator Pair -Generator

- -Sometimes a mutable/const pair of iterator types is needed, such as -when implementing a container type. The -projection_iterator_pair_generator class makes it more -convenient to create this pair of iterator types. - -
-template <class AdaptableUnaryFunction, class BaseIterator, class ConstBaseIterator>
-class projection_iterator_pair_generator
-{
-public:
-  typedef iterator_adaptor<...> iterator;       // the mutable projection iterator type 
-  typedef iterator_adaptor<...> const_iterator; // the immutable projection iterator type 
-};
-
- -

Example

- -In this part of the example we use the -projection_iterator_pair_generator to create a mutable/const -pair of projection iterators that access the ID numbers of the -personnel. We use the mutable iterator to re-index the ID numbers from -zero. We then use the constant iterator to print the ID numbers out. - -
-  // continuing from the last example...
-
-  typedef boost::projection_iterator_pair_generator<select_ID,
-    std::list<personnel_record>::iterator,
-    std::list<personnel_record>::const_iterator> PairGen;
-
-  PairGen::iterator ID_first(personnel_list.begin()),
-    ID_last(personnel_list.end());
-
-  int new_id = 0;
-  while (ID_first != ID_last) {
-    *ID_first = new_id++;
-    ++ID_first;
-  }
-
-  PairGen::const_iterator const_ID_first(personnel_list.begin()),
-    const_ID_last(personnel_list.end());
-
-  std::copy(const_ID_first, const_ID_last,
-            std::ostream_iterator<int>(std::cout, " "));
-  std::cout << std::endl;
-  std::cout << std::endl;
-  
-  // to be continued...
-
-0 1 2 3 
-
- -

Template Parameters

- - - - - - - - - - - - - - - - - - - - - - - -
ParameterDescription
AdaptableUnaryFunctionThe type of the function object. The argument_type of the -function must match the value type of the base iterator. The function -should return a true reference to the function's result_type. -The result_type will be the resulting iterator's value_type. -
BaseIteratorThe mutable iterator type being wrapped.
ConstBaseIteratorThe constant iterator type being wrapped.
- -

Model of

- -If the base iterator types model the Random -Access Iterator then so do the resulting projection iterator -types. If the base iterators support less functionality the -resulting projection iterator types will also support less -functionality. The resulting iterator type is mutable, and -the resulting const_iterator type is constant. - -

Members

- -The resulting iterator and const_iterator types -implements the member functions and operators required of the Random -Access Iterator concept. In addition they support the following -constructors: - -
-projection_iterator_pair_generator::iterator(const BaseIterator& it,
-                                             const AdaptableUnaryFunction& p = AdaptableUnaryFunction())
- -
-projection_iterator_pair_generator::const_iterator(const BaseIterator& it,
-                                                   const AdaptableUnaryFunction& p = AdaptableUnaryFunction())
-
- -

-


-

- -

The Projection Iterator Object Generators

- -The make_projection_iterator() and -make_const_projection_iterator() functions provide a more -convenient way to create projection iterator objects. The functions -save the user the trouble of explicitly writing out the iterator -types. - -
-template <class AdaptableUnaryFunction, class BaseIterator>
-typename projection_iterator_generator<AdaptableUnaryFunction, BaseIterator>::type
-make_projection_iterator(BaseIterator base,
-			 const AdaptableUnaryFunction& p = AdaptableUnaryFunction())  
-
-template <class AdaptableUnaryFunction, class ConstBaseIterator>
-typename projection_iterator_generator<AdaptableUnaryFunction, ConstBaseIterator>::type
-make_const_projection_iterator(ConstBaseIterator base,
-			       const AdaptableUnaryFunction& p = AdaptableUnaryFunction())  
-
- - -

Example

- -In this part of the example, we again print out the names of the -personnel, but this time we use the -make_const_projection_iterator() function to save some typing. - -
-  // continuing from the last example...
-
-  std::copy
-    (boost::make_const_projection_iterator<select_name>(personnel_list.begin()),
-     boost::make_const_projection_iterator<select_name>(personnel_list.end()),
-     std::ostream_iterator(std::cout, "\n"));
-
-  return 0;
-}
-
-The output is: -
-Barney
-Fred
-Wilma
-Betty
-
- -
-

Revised 19 Aug 2001

-

© Copyright Jeremy Siek 2000. Permission to copy, use, -modify, sell and distribute this document is granted provided this copyright -notice appears in all copies. This document is provided "as is" -without express or implied warranty, and with no claim as to its suitability for -any purpose.

- - - - - - - - diff --git a/reverse_iterator.htm b/reverse_iterator.htm deleted file mode 100644 index d20735f..0000000 --- a/reverse_iterator.htm +++ /dev/null @@ -1,331 +0,0 @@ - - - - - - - - - - Reverse Iterator Adaptor Documentation - - - - c++boost.gif (8819 bytes) - -

Reverse Iterator Adaptor

- Defined in header boost/iterator_adaptors.hpp - -

The reverse iterator adaptor flips the direction of a base iterator's - motion. Invoking operator++() moves the base iterator backward and - invoking operator--() moves the base iterator forward. The Boost - reverse iterator adaptor is better to use than the - std::reverse_iterator class in situations where pairs of - mutable/constant iterators are needed (e.g., in containers) because - comparisons and conversions between the mutable and const versions are - implemented correctly. - -

Synopsis

-
-namespace boost {
-  template <class BidirectionalIterator,
-            class Value, class Reference, class Pointer, class Category, class Distance>
-  struct reverse_iterator_generator;
-  
-  template <class BidirectionalIterator>
-  typename reverse_iterator_generator<BidirectionalIterator>::type
-  make_reverse_iterator(BidirectionalIterator base)  
-}
-
-
- -

The Reverse Iterator Type - Generator

- The reverse_iterator_generator template is a generator of - reverse iterator types. The main template parameter for this class is the - base BidirectionalIterator type that is being adapted. In most - cases the associated types of the base iterator can be deduced using - std::iterator_traits, but in some situations the user may want to - override these types, so there are also template parameters for the base - iterator's associated types. - -
-
-template <class BidirectionalIterator,
-          class Value, class Reference, class Pointer, class Category, class Distance>
-class reverse_iterator_generator
-{
-public:
-  typedef iterator_adaptor<...> type; // the resulting reverse iterator type 
-};
-
-
- -

Example

- In this example we sort a sequence of letters and then output the sequence - in descending order using reverse iterators. - -
-
-#include <boost/config.hpp>
-#include <iostream>
-#include <algorithm>
-#include <boost/iterator_adaptors.hpp>
-
-int main(int, char*[])
-{
-  char letters[] = "hello world!";
-  const int N = sizeof(letters)/sizeof(char) - 1;
-  std::cout << "original sequence of letters:\t"
-      << letters << std::endl;
-
-  std::sort(letters, letters + N);
-
-  // Use reverse_iterator_generator to print a sequence
-  // of letters in reverse order.
-  
-  boost::reverse_iterator_generator<char*>::type
-    reverse_letters_first(letters + N),
-    reverse_letters_last(letters);
-
-  std::cout << "letters in descending order:\t";
-  std::copy(reverse_letters_first, reverse_letters_last,
-      std::ostream_iterator<char>(std::cout));
-  std::cout << std::endl;
-
-  // to be continued...
-
-
- The output is: - -
-
-original sequence of letters: hello world!
-letters in descending order:  wroolllhed! 
-
-
- -

Template Parameters

- - - - - - - - - -
Parameter - - Description - -
BidirectionalIterator - - - The iterator type being wrapped. - -
Value - - The value-type of the base iterator and the resulting reverse - iterator.
- Default:std::iterator_traits<BidirectionalIterator>::value_type - - -
Reference - - The reference type of the resulting iterator, and in - particular, the result type of operator*().
- Default: If Value is supplied, Value& is - used. Otherwise - std::iterator_traits<BidirectionalIterator>::reference - is used. - -
Pointer - - The pointer type of the resulting iterator, and in - particular, the result type of operator->().
- Default: If Value was supplied, then Value*, - otherwise - std::iterator_traits<BidirectionalIterator>::pointer. - -
Category - - The iterator_category type for the resulting iterator.
- Default: - std::iterator_traits<BidirectionalIterator>::iterator_category - - -
Distance - - The difference_type for the resulting iterator.
- Default: - std::iterator_traits<BidirectionalIterator&gt::difference_type - -
- -

Concept Model

- The indirect iterator will model whichever standard iterator concept - category is modeled by the base iterator. Thus, if the base iterator is - a model of Random Access - Iterator then so is the resulting indirect iterator. If the base - iterator models a more restrictive concept, the resulting indirect iterator - will model the same concept. The base iterator must be at least a Bidirectional - Iterator - -

Members

- The reverse iterator type implements the member functions and operators - required of the Random Access - Iterator concept. In addition it has the following constructor: - -
-
-reverse_iterator_generator::type(const BidirectionalIterator& it)
-
-
- - -
-
- -
- -

- -

The Reverse Iterator Object - Generator

- The make_reverse_iterator() function provides a more convenient - way to create reverse iterator objects. The function saves the user the - trouble of explicitly writing out the iterator types. - -
-
-template <class BidirectionalIterator>
-typename reverse_iterator_generator<BidirectionalIterator>::type
-make_reverse_iterator(BidirectionalIterator base);
-
-
- -

Example

- In this part of the example we use make_reverse_iterator() to - print the sequence of letters in reverse-reverse order, which is the - original order. - -
-
-  // continuing from the previous example...
-
-  std::cout << "letters in ascending order:\t";
-  std::copy(boost::make_reverse_iterator(reverse_letters_last),
-      boost::make_reverse_iterator(reverse_letters_first),
-      std::ostream_iterator<char>(std::cout));
-  std::cout << std::endl;
-
-  return 0;
-}
-
-
- The output is: - -
-
-letters in ascending order:  !dehllloorw
-
-
-
- -

Constant/Mutable Iterator Interactions

- -

One failing of the standard reverse_iterator - adaptor is that it doesn't properly support interactions between adapted - const and non-const iterators. For example: -

-
-#include <vector>
-
-template <class T> void convert(T x) {}
-
-// Test interactions of a matched pair of random access iterators
-template <class Iterator, class ConstIterator>
-void test_interactions(Iterator i, ConstIterator ci)
-{
-  bool eq = i == ci;               // comparisons
-  bool ne = i != ci;            
-  bool lt = i < ci;
-  bool le = i <= ci;
-  bool gt = i > ci;
-  bool ge = i >= ci;
-  std::size_t distance = i - ci;   // difference
-  ci = i;                          // assignment
-  ConstIterator ci2(i);            // construction
-  convert<ConstIterator>(i);       // implicit conversion
-}
-
-void f()
-{
-  typedef std::vector<int> vec;
-  vec v;
-  const vec& cv;
-
-  test_interactions(v.begin(), cv.begin());   // OK
-  test_interactions(v.rbegin(), cv.rbegin()); // ERRORS ON EVERY TEST!!
-
-
-Reverse iterators created with boost::reverse_iterator_generator don't have this problem, though: -
-
-  typedef boost::reverse_iterator_generator<vec::iterator>::type ri;
-  typedef boost::reverse_iterator_generator<vec::const_iterator>::type cri;
-  test_interactions(ri(v.begin()), cri(cv.begin()));   // OK!!
-
-
-Or, more simply, -
-
-  test_interactions(
-    boost::make_reverse_iterator(v.begin()), 
-    boost::make_reverse_iterator(cv.begin()));   // OK!!
-}
-
-
- -

If you are wondering why there is no -reverse_iterator_pair_generator in the manner of projection_iterator_pair_generator, -the answer is simple: we tried it, but found that in practice it took -more typing to use reverse_iterator_pair_generator than to -simply use reverse_iterator_generator twice!

- -


- - -

Revised - 19 Aug 2001 - - -

© Copyright Jeremy Siek 2000. Permission to copy, use, modify, sell - and distribute this document is granted provided this copyright notice - appears in all copies. This document is provided "as is" without express or - implied warranty, and with no claim as to its suitability for any purpose. - - - - - - - diff --git a/transform_iterator.htm b/transform_iterator.htm deleted file mode 100644 index 4b3dce3..0000000 --- a/transform_iterator.htm +++ /dev/null @@ -1,223 +0,0 @@ - - - - - - -Transform Iterator Adaptor Documentation - - - - -c++boost.gif (8819 bytes) - -

Transform Iterator Adaptor

- -Defined in header -boost/iterator_adaptors.hpp - -

-The transform iterator adaptor augments an iterator by applying some -function object to the result of dereferencing the iterator. In other -words, the operator* of the transform iterator first -dereferences the base iterator, passes the result of this to the -function object, and then returns the result. The following -pseudo-code shows the basic idea: - -

-  value_type transform_iterator::operator*() const {
-    return this->f(*this->base_iterator);
-  }
-
- -All of the other operators of the transform iterator behave in the -same fashion as those of the base iterator. - - -

Synopsis

- -
-namespace boost {
-  template <class AdaptableUnaryFunction, class BaseIterator>
-  class transform_iterator_generator;
-
-  template <class AdaptableUnaryFunction, class BaseIterator>
-  typename transform_iterator_generator<AdaptableUnaryFunction,Iterator>::type
-  make_transform_iterator(BaseIterator base, const AdaptableUnaryFunction& f = AdaptableUnaryFunction());
-}
-
- -
- -

The Transform Iterator Type -Generator

- -The class transform_iterator_generator is a helper class whose -purpose is to construct a transform iterator type. The template -parameters for this class are the AdaptableUnaryFunction function object -type and the BaseIterator type that is being wrapped. - -
-template <class AdaptableUnaryFunction, class Iterator>
-class transform_iterator_generator
-{
-public:
-    typedef iterator_adaptor<...> type;
-};
-
- -

Example

- -

-The following is an example of how to use the -transform_iterator_generator class to iterate through a range -of numbers, multiplying each of them by 2 when they are dereferenced. -The boost::binder1st class is used instead of the standard -one because tranform iterator requires the function object to be -Default Constructible. - -

-

-#include <functional>
-#include <iostream>
-#include <boost/iterator_adaptors.hpp>
-
-// definition of class boost::binder1st and function boost::bind1st() ...
-
-int
-main(int, char*[])
-{
-  int x[] = { 1, 2, 3, 4, 5, 6, 7, 8 };
-
-  typedef boost::binder1st< std::multiplies<int> > Function;
-  typedef boost::transform_iterator_generator<Function, int*>::type doubling_iterator;
-
-  doubling_iterator i(x, boost::bind1st(std::multiplies<int>(), 2)),
-    i_end(x + sizeof(x)/sizeof(int), boost::bind1st(std::multiplies<int>(), 2));
-
-  std::cout << "multiplying the array by 2:" << std::endl;
-  while (i != i_end)
-    std::cout << *i++ << " ";
-  std::cout << std::endl;
-
-  // to be continued...
-
-The output from this part is: -
-2 4 6 8 10 12 14 16
-
- -

Template Parameters

- - - - - - - - - - - - - - - - -
ParameterDescription
AdaptableUnaryFunctionThe function object that transforms each element in the iterator -range. The argument_type of the function object must match -the value type of the base iterator. The result_type of the -function object will be the resulting iterator's -value_type. If you want the resulting iterator to behave as -an iterator, the result of the function should be solely a function of -its argument. Also, the function object must be Default -Constructible (which many of the standard function objects are not).
BaseIteratorThe iterator type being wrapped. This type must at least be a model - of the InputIterator concept.
- -

Model of

- -The transform iterator adaptor (the type -transform_iterator_generator<...>::type) is a model of Input Iterator[1]. - - -

Members

- -The transform iterator type implements the member functions and -operators required of the Random Access Iterator -concept, except that the reference type is the same as the value_type -so operator*() returns by-value. In addition it has the following constructor: - -
-transform_iterator_generator::type(const BaseIterator& it,
-                                   const AdaptableUnaryFunction& f = AdaptableUnaryFunction())
-
- -

-


-

- - -

The Transform Iterator Object Generator

- -
-template <class AdaptableUnaryFunction, class BaseIterator>
-typename transform_iterator_generator<AdaptableUnaryFunction,BaseIterator>::type
-make_transform_iterator(BaseIterator base,
-                        const AdaptableUnaryFunction& f = AdaptableUnaryFunction());
-
- -This function provides a convenient way to create transform iterators. - -

Example

- -Continuing from the previous example, we use the make_transform_iterator() -function to add four to each element of the array. - -
-  std::cout << "adding 4 to each element in the array:" << std::endl;
-
-  std::copy(boost::make_transform_iterator(x, boost::bind1st(std::plus(), 4)),
-	    boost::make_transform_iterator(x + N, boost::bind1st(std::plus(), 4)),
-	    std::ostream_iterator(std::cout, " "));
-  std::cout << std::endl;
-
-  return 0;
-}
-
-The output from this part is: -
-5 6 7 8 9 10 11 12
-
- -

Notes

- - -[1] If the base iterator is a model of Random Access Iterator -then the transform iterator will also suppport most of the -functionality required by the Random Access Iterator concept. However, a -transform iterator can never completely satisfy the requirements for -Forward Iterator -(or of any concepts that refine Forward Iterator, which includes -Random Access Iterator and Bidirectional Iterator) since the operator* of the transform -iterator always returns by-value. - - - -
-

Revised 19 Aug 2001

-

© Copyright Jeremy Siek 2000. Permission to copy, use, -modify, sell and distribute this document is granted provided this copyright -notice appears in all copies. This document is provided "as is" -without express or implied warranty, and with no claim as to its suitability for -any purpose.

- - - -