PageRenderTime 15ms CodeModel.GetById 10ms app.highlight 3ms RepoModel.GetById 1ms app.codeStats 0ms

/Src/Dependencies/Boost/libs/iterator/doc/quickbook/shared_container_iterator.qbk

http://hadesmem.googlecode.com/
text | 248 lines | 174 code | 74 blank | 0 comment | 0 complexity | 46632f21f6d9b8833c5da3fddc04ffa0 MD5 | raw file
  1
  2[section:shared_container Shared Container Iterator]
  3
  4Defined in header [@../../../boost/shared_container_iterator.hpp `boost/shared_container_iterator.hpp`].
  5
  6The purpose of the shared container iterator is to attach the lifetime
  7of a container to the lifetime of its iterators. In other words, the
  8container will not be deleted until after all its iterators are
  9destroyed. The shared container iterator is typically used to
 10implement functions that return iterators over a range of objects that
 11only need to exist for the lifetime of the iterators. By returning a
 12pair of shared iterators from a function, the callee can return a
 13heap-allocated range of objects whose lifetime is automatically
 14managed.
 15
 16The shared container iterator augments an iterator over a shared
 17container. It maintains a reference count on the shared container. If
 18only shared container iterators hold references to the container, the
 19container's lifetime will end when the last shared container iterator
 20over it is destroyed. In any case, the shared container is guaranteed
 21to persist beyond the lifetime of all the iterators. In all other
 22ways, the shared container iterator behaves the same as its base
 23iterator.
 24
 25[h2 Synopsis]
 26
 27  namespace boost {
 28    template <typename Container>
 29    class shared_container_iterator;
 30   
 31    template <typename Container>
 32    shared_container_iterator<Container>
 33    make_shared_container_iterator(typename Container::iterator base, 
 34      boost::shared_ptr<Container> const& container);
 35   
 36    std::pair<
 37      typename shared_container_iterator<Container>,
 38      typename shared_container_iterator<Container>
 39    >
 40    make_shared_container_range(boost::shared_ptr<Container> const& container);
 41  }
 42
 43[section:shared_container_type The Shared Container Iterator Type]
 44
 45  template <typename Container> class shared_container_iterator;
 46
 47The class template `shared_container_iterator` is the shared container
 48iterator type. The `Container` template type argument must model the
 49[@http://www.sgi.com/tech/stl/Container.html Container] concept. 
 50
 51[h2 Example]
 52
 53The following example illustrates how to create an iterator that
 54regulates the lifetime of a reference counted `std::vector`. Though the
 55original shared pointer `ints` ceases to exist after `set_range()`
 56returns, the `shared_counter_iterator` objects maintain references to
 57the underlying vector and thereby extend the container's lifetime.
 58
 59[@../../../libs/utility/shared_iterator_example1.cpp `shared_iterator_example1.cpp`]:
 60
 61  #include "shared_container_iterator.hpp"
 62  #include "boost/shared_ptr.hpp"
 63  #include <algorithm>
 64  #include <iostream>
 65  #include <vector>
 66   
 67  typedef boost::shared_container_iterator< std::vector<int> > iterator;
 68   
 69   
 70  void set_range(iterator& i, iterator& end)  {
 71   
 72    boost::shared_ptr< std::vector<int> > ints(new std::vector<int>());
 73    
 74    ints->push_back(0);
 75    ints->push_back(1);
 76    ints->push_back(2);
 77    ints->push_back(3);
 78    ints->push_back(4);
 79    ints->push_back(5);
 80    
 81    i = iterator(ints->begin(),ints);
 82    end = iterator(ints->end(),ints);
 83  }
 84   
 85   
 86  int main() {
 87   
 88    iterator i,end;
 89   
 90    set_range(i,end);
 91   
 92    std::copy(i,end,std::ostream_iterator<int>(std::cout,","));
 93    std::cout.put('\n');
 94   
 95    return 0;
 96  }
 97
 98The output from this part is:
 99
100  0,1,2,3,4,5,
101
102[table Template Parameters
103  [[Parameter][Description]]
104  [[Container][The type of the container that we wish to iterate over. It must be a model of the Container concept.]]
105]
106
107[h2 Concepts]
108
109The `shared_container_iterator` type models the same iterator concept
110as the base iterator (`Container::iterator`).
111
112[h2 Operations]
113
114The `shared_container_iterator` type implements the member functions
115and operators required of the
116[@http://www.sgi.com/tech/stl/RandomAccessIterator.html Random Access
117Iterator] concept, though only operations defined for the base
118iterator will be valid. In addition it has the following constructor:
119
120  shared_container_iterator(Container::iterator const& it,
121                            boost::shared_ptr<Container> const& container)
122
123[endsect]
124
125[section:shared_container_object_generator The Shared Container Iterator Object Generator]
126
127  template <typename Container>
128  shared_container_iterator<Container>
129  make_shared_container_iterator(Container::iterator base,
130                                 boost::shared_ptr<Container> const& container)
131
132This function provides an alternative to directly constructing a
133`shared_container_iterator`. Using the object generator, a 
134`shared_container_iterator` can be created and passed to a function without
135explicitly specifying its type.
136
137[h2 Example]
138
139This example, similar to the previous, 
140uses `make_shared_container_iterator()` to create the iterators.
141
142[@../../../libs/utility/shared_iterator_example2.cpp `shared_iterator_example2.cpp`]:
143
144  #include "shared_container_iterator.hpp"
145  #include "boost/shared_ptr.hpp"
146  #include <algorithm>
147  #include <iterator>
148  #include <iostream>
149  #include <vector>
150   
151   
152  template <typename Iterator>
153  void print_range_nl (Iterator begin, Iterator end) {
154    typedef typename std::iterator_traits<Iterator>::value_type val;
155    std::copy(begin,end,std::ostream_iterator<val>(std::cout,","));
156    std::cout.put('\n');
157  }
158   
159   
160  int main() {
161   
162    typedef boost::shared_ptr< std::vector<int> > ints_t;
163    {
164      ints_t ints(new std::vector<int>());
165   
166      ints->push_back(0);
167      ints->push_back(1);
168      ints->push_back(2);
169      ints->push_back(3);
170      ints->push_back(4);
171      ints->push_back(5);
172   
173      print_range_nl(boost::make_shared_container_iterator(ints->begin(),ints),
174                     boost::make_shared_container_iterator(ints->end(),ints));
175    }
176    
177   
178   
179    return 0;
180  }
181
182Observe that the `shared_container_iterator` type is never explicitly
183named. The output from this example is the same as the previous.
184
185[endsect]
186
187[section:shared_container_generator The Shared Container Iterator Range Generator]
188
189  template <typename Container>
190  std::pair<
191    shared_container_iterator<Container>,
192    shared_container_iterator<Container>
193  >
194  make_shared_container_range(boost::shared_ptr<Container> const& container);
195  Class shared_container_iterator is meant primarily to return, using iterators, a range of values that we can guarantee will be alive as long as the iterators are. This is a convenience function to do just that. It is equivalent to
196  std::make_pair(make_shared_container_iterator(container->begin(),container),
197                 make_shared_container_iterator(container->end(),container));
198
199[h2 Example]
200
201In the following example, a range of values is returned as a pair of shared_container_iterator objects.
202
203[@../../../libs/utility/shared_iterator_example3.cpp `shared_iterator_example3.cpp`]:
204
205  #include "shared_container_iterator.hpp"
206  #include "boost/shared_ptr.hpp"
207  #include "boost/tuple/tuple.hpp" // for boost::tie
208  #include <algorithm>              // for std::copy
209  #include <iostream>              
210  #include <vector>
211   
212   
213  typedef boost::shared_container_iterator< std::vector<int> > iterator; 
214   
215  std::pair<iterator,iterator>
216  return_range() {
217    boost::shared_ptr< std::vector<int> > range(new std::vector<int>());
218    range->push_back(0);
219    range->push_back(1);
220    range->push_back(2);
221    range->push_back(3);
222    range->push_back(4);
223    range->push_back(5);
224    return boost::make_shared_container_range(range);
225  }
226   
227   
228  int main() {
229   
230   
231    iterator i,end;
232    
233    boost::tie(i,end) = return_range();
234   
235    std::copy(i,end,std::ostream_iterator<int>(std::cout,","));
236    std::cout.put('\n');
237   
238    return 0;
239  }
240
241Though the range object only lives for the duration of the
242`return_range` call, the reference counted `std::vector` will live
243until `i` and `end` are both destroyed. The output from this example is
244the same as the previous two.
245
246[endsect]
247
248[endsect]