The use of "valid but unspecified" as a guarantee is useless and damaging. Consider std::list<>
. A guarantee of std::list<>
is that on move the iterators are not invalidated (different use of valid), except for the end iterator. The end iterator frequently points directly to an empty terminal node directly in the local instance so moving a list invalidates the end iterator. Invalidation can be a source of bugs so a library implementor decided their implementation would strengthen the guarantee by ensuring that the end iterator was valid even with a move. To do so, they heap-allocate the terminal node for each list.
If you move-construct this list, the rhs argument must be "valid but unspecified". To achieve that, an end node must be allocated in the rhs. Now the move constructor is not noexcept
. Not having a noexcept
move constructor is problematic because it makes it impossible to get robust transactional behavior to restore a system after a throw. Trying to complete a transaction by moving in the r