
The Standard's table of InputIterator requirements (table 72 in section 24.1) says that, amongst other things, an InputIterator must support the following two expressions: *a Convertible to T, the iterator's value_type a->m Equivalent to (*a).m The same language is present in the "New Iterator Concepts", N1550, documentation in the definition of ReadableIterator. In particular, InputIterators are allowed to, and often do, have operator* returning by value: template <typename T> class my_iterator { public: typedef T value_type; T operator*() const; // ... }; Because it is legal to call non-const member functions on temporary objects, it is legal to call non-const member functions on the value returned from operator*: struct foo { void non_const(); }; my_iterator<foo> i; (*i).non_const(); My reading of Table 72 documentation suggests that this means that for my_iterator<foo> to be a Readable Iterator, it must also be legal to write: i->non_const(); If so, this means that operator-> should return T* instead of T const* (possibly via a proxy class). In the current implementation of boost::iterator_facade, operator-> returns a proxy that acts as a T const*: template <class T> struct operator_arrow_proxy { operator_arrow_proxy(T const* px) : m_value(*px) {} const T* operator->() const { return &m_value; } operator const T*() const { return &m_value; } T m_value; }; Is there a reason not to change this to have operator-> returning a T*? That would seem closer to the defintion of an InputIterator. (I supposed that if operator* returns by const value, it would be necessary to resurrect the constness in the proxy, but assuming the iterator's reference typedef is also a const-qualified value, this should be easy enough.) I had a look at the current concept-based iterator proposal, N2039, to see whether that shed any light on this and it also seems to require this behaviour from an InputIterator. It formal concept only requires operator->'s return to be convertible to T const* (which T*, or a proxy to T*, is): concept InputIterator<typename X> { where /*...*/ Convertible<pointer, value_type const*>; pointer operator->(X); // } And in it's definition of operator->, it requires (*a).m to be well-formed and then defines a->m to be equivalent to it. Have I misunderstood some aspect of this, or does the Standard really all require that a generic input iterator adaptor, such as boost::iterator_adaptor (and by impliciation boost::iterator_facade) should support this? -- Richard Smith