
On Sat, Nov 22, 2008 at 13:12, Tomas Puverle <Tomas.Puverle@morganstanley.com> wrote:
But what semantics for empty *are* documented?
http://www.boost.org/doc/libs/1_37_0/libs/range/doc/boost_range.html empty(x) returns boost::begin(x) == boost::end(x)
Prior to 1.35, the iterator_range<> documentation read the following:
"Recall that many default constructed iterators are singular and hence can only be assigned, but not compared or incremented or anything. However, if one creates a default constructed iterator_range, then one can still call all its member functions. This means that the iterator_range will still be usable in many contexts even though the iterators underneath are not. "
Does this answer your question?
Thank you; I hadn't noticed that. However, the documentation for both says that "The intention of the iterator_range class is to encapsulate two iterators so they fulfill the Forward Range concept," given a template argument that matches the ForwardTraversalIterator concept. The problem, then, is that neither the 1.34 nor 1.35 implementation satisfies the requirements for the Forward Range concept given an iterator such as the following, despite it being, as far as I can tell, a perfectly legal Forward Traversal Iterator: template <typename T> struct contrived_iterator { shared_ptr<T> x; bool dirty; contrived_iterator() : x(new T()), dirty() {} contrived_iterator(contrived_iterator const &i) : x(i.x), dirty(i.dirty) {} contrived_iterator &operator=(contrived_iterator const &i) { x = i.x; dirty = i.dirty; } contrived_iterator &operator++() { dirty = true; } contrived_iterator operator++(int) { contrived_iterator i = *this; ++*this; return i; } bool operator==(contrived_iterator i) { return dirty || i.dirty; } bool operator!=(contrived_iterator i) { return !(*this == i); } T &operator*() { return *x; } T const &operator*() { return *x; } typedef int difference_type; typedef T value_type typedef T& reference; } template <typename T> struct iterator_traversal<contrived_iterator<T> > { typedef forward_traversal_tag type; } It seems there's an assumption that a default-constructed iterator is either singular or past-the-end, but I saw no such requirement in either the standard or the "New iterator concepts" document.