Why should iterators be CopyConstructible and CopyAssignable?

According to en.cppreference.com and VC ++ 14.0, iterators need to have copy constructors and copy assignment operators.

My iterator class (iterating through Windows processes) cannot ever be constructive or copyable - it saves a HANDLE for the snapshot and controls the release of it, so it is impossible to copy them - moving them is possible, I set the move constructor and move the assignment operator. However, the std::find_if copies them (in VC ++ 14.0 there are some std::_Find_if that require copying an iterator) and do not want to work.

Why does your iterator support the resource? The iterator should be like a pointer, where it points to something.

Since you need to create a snapshot to iterate through Windows processes, and then use it for this, the problem is one snapshot, one iteration. Also, the picture is not copied.

Why can't they be MoveConstructible and MoveAssignable ? What algorithms (if any) really need to copy iterators?

+6
source share
3 answers

TL DR: Due to historical reasons.

I think it is more or less obvious why ForwardIterator and other more functional iterators should be copyable. As for InputIterator and OutputIterator , the situation is a bit more complicated.

InputIterator and OutputIterator have a one-pass nature, which goes well with the concept of a motion-only class. Now, when you use any of these iterators from the standard library (say, istream_iterator for example), you can copy it and dereference the copy, but promoting any of the copies will advance all of them, which does not look like the expected behavior.

Unfortunately, at the time of writing many STL algorithms (for example, std::find_if , std::copy , etc.) there was no movement semantics at all, and there was no way to require that InputIterator constructive.

Since then, on some platforms, STL algorithms actually require the iterator to be specified as copyable (as in this case), as well as on other platforms (for example, g ++ AFAIK), this behavior is required by the concept of InputIterator , which is checked at compile time every time when you use STL algorithms.

In addition, you may find this answer helpful.

+3
source

Iterators should not contain resources; they are pointer abstractions and should be cheap to copy. This standard library assumes this.

Use a separate (only for moving) class to control HANDLE ; your iterators should keep a pointer to this class.

+2
source

Well, how can they be? The simplest possible find would look something like this:

 for (IT i = begin_iterator, e = end_iterator; i != e; ++i) 

And how would he build i?

-1
source

All Articles