The behavior of swap is much clarified in C ++ 11, largely to allow the standard library algorithms to use dependency-dependent search (ADL) to search for swap functions for user types. C ++ 11 adds the concept of swappable (C ++ 11 §17.6.3.2 [swappable.requirements]) to make this legal (and mandatory).
The text in the standard C ++ 11 language that answers your question is the following text from the requirements of the container (§23.2.1 [container.requirements.general] / 8) that defines the behavior of the swap container member function:
Each iterator that refers to an element in one container before the swap must refer to the same element in another container after the exchange.
It is not indicated whether there will be an iterator with a.end() value before swap has b.end() value after the swap.
Your example guarantees that a will be valid after the exchange, but b not because it is an end iterator. The reason that iterators end is not guaranteed to be valid, is explained in the note in §23.2.1 / 10:
[Note: the end() iterator does not refer to any element, therefore it can be nullified. - note]
This is the same behavior that is defined in C ++ 03, just clarified. The source language from C ++ 03 is in C ++ 03 §23.1 / 10:
Functionno swap() invalidates any references, pointers, or iterators that reference elements of exchanged containers.
This is not immediately visible in the source text, but the phrase "container elements" is extremely important because end() iterators do not point to elements.
James McNellis Nov 08 '10 at 3:23 a.m. 2010-11-08 15:23
source share