This page is a snapshot from the LWG issues list, see the Library Active Issues List for more information and the meaning of C++11 status.
swap
undefined for most containersSection: 23 [containers] Status: C++11 Submitter: Alisdair Meredith Opened: 2008-01-14 Last modified: 2016-01-28
Priority: Not Prioritized
View other active issues in [containers].
View all other issues in [containers].
View all issues with C++11 status.
Discussion:
It appears most containers declare but do not define a member-swap function.
This is unfortunate, as all overload the swap
algorithm to call the
member-swap function!
(required for swappable
guarantees [Table 37] and Container Requirements
[Table 87])
Note in particular that Table 87 gives semantics of a.swap(b)
as swap(a,b)
,
yet for all containers we define swap(a,b)
to call a.swap(b)
- a circular
definition.
A quick survey of clause 23 shows that the following containers provide a definition for member-swap:
array queue stack vector
Whereas the following declare it, but do not define the semantics:
deque list map multimap multiset priority_queue set unordered_map unordered_multi_map unordered_multi_set unordered_set
Suggested resolution:
Provide a definition for each of the affected containers...
[ Bellevue: ]
Move to Open and ask Alisdair to provide wording.
[ 2009-07 Frankfurt: ]
Daniel to provide wording. N2590 is no longer applicable.
[ 2009-07-28 Daniel provided wording. ]
- It assumes that the proposed resolution for 883(i) is applied, which breaks the circularity of definition between member
swap
and freeswap
.- It uses the notation of the pre-concept allocator trait
allocator_propagation_map
, which might be renamed after the next refactoring phase of generalized allocators.- It requires that compare objects, key equal functions and hash functions in containers are swapped via unqualified free
swap
according to 594(i).
[ 2009-09-30 Daniel adds: ]
The outcome of this issue should be considered with the outcome of 1198(i) both in style and in content (e.g. bullet 9 suggests to define the semantic of
void priority_queue::swap(priority_queue&)
in terms of the memberswap
of the container).
[ 2009-10 Santa Cruz: ]
Looked at, but took no action on as it overlaps too much with N2982. Waiting for a new draft WP.
[ 2009-10 Santa Cruz: ]
Leave as open. Pablo to provide wording.
[ 2009-10-26 Pablo updated wording. Here is the wording he replaced: ]
Add a new Throws clause just after 99 [allocator.propagation.map]/5:
static void swap(Alloc& a, Alloc& b);Effects: [..]
[ This exception requirement is added, such that it's combination with the general container requirements of N2723 [container.requirements.general]/9 make it unambiguously clear that the following descriptions of "swaps the allocators" have the following meaning: (a) This swap is done by calling
allocator_propagation_map<allocator_type>::swap
and (b) This allocator swap does never propagate an exception ]Change 23.2.7.2 [associative.reqmts.except]/3 as indicated:
For associative containers, no
swap
function throws an exception unless that exception is thrown by thecopy constructor or copy assignment operatorof the container'sPred
object(if any).Change 23.2.8.2 [unord.req.except]/3 as indicated:
For unordered associative containers, no
swap
function throws an exception unless that exception is thrown by thecopy constructor or copy assignment operatorof the container'sHash
orPred
object(if any).Insert a new paragraph just after 23.3 [sequences]/1:
[ There is a new issue in process that will suggest a minimum header for
swap
andmove
. If this one is provided, this text can be removed and the header dependency should be added to<queue>
]Add one further clause at the end of 23.3.3.4 [array.special]:
[This part is added, because otherwise
array::swap
would otherwise contradict the general contract of 23.2.2 [container.requirements.general] p. 10 b. 5]
In 23.3.5 [deque], class template
deque
synopsis change as indicated:void swap(deque<T,Alloc>&);At the end of 23.3.5.4 [deque.modifiers] add as indicated:
In [forwardlist], class template
forward_list
synopsis change as indicated:void swap(forward_list<T,Allocator>&);At the end of [forwardlist.modifiers] add as indicated:
In 23.3.11 [list], class template
list
synopsis change as indicated:void swap(list<T,Allocator>&);At the end of 23.3.11.4 [list.modifiers] add as indicated:
At the end of 23.6.4.4 [priqueue.members] add a new prototype description:
[ This requirement is added to ensure that even a user defined
swap
which is found by ADL forCompare
satisfies theSwappable
requirements ]
[ This part is added, because otherwise
priority_queue::swap
would otherwise contradict the general contract of 23.2.2 [container.requirements.general] p. 10 b. 5 ]
In 23.3.13 [vector], class template
vector
synopsis change as indicated:void swap(vector<T,Allocator>&);Change 23.3.13.3 [vector.capacity] p. 8 as indicated:
void swap(vector<T,Allocator>& x);Effects: Exchanges the contents and
capacity()
of*this
with that ofx
.Insert a new paragraph just before 23.4 [associative]/1:
In 23.4.3 [map], class template
map
synopsis change as indicated:void swap(map<Key,T,Compare,Allocator>&);At the end of 23.4.3.4 [map.modifiers] add as indicated:
[ This requirement is added to ensure that even a user defined
swap
which is found by ADL forCompare
satisfies theSwappable
requirements ]
In 23.4.4 [multimap], class template
multimap
synopsis change as indicated:void swap(multimap<Key,T,Compare,Allocator>&);At the end of 23.4.4.3 [multimap.modifiers] add as indicated:
In 23.4.6 [set], class template
set
synopsis change as indicated:void swap(set<Key,Compare,Allocator>&);After section 23.4.6.2 [set.cons] add a new section and add the following paragraphs:
In 23.4.7 [multiset], class template
multiset
synosis, change as indicated:void swap(multiset<Key,Compare,Allocator>&);After section 23.4.7.2 [multiset.cons] add a new section and add the following paragraphs:
Insert a new paragraph just before 23.5 [unord] p. 1:
After section 23.5.3.3 [unord.map.elem] add a new section and add the following paragraphs:
[ This requirement is added to ensure that even a user defined
swap
which is found by ADL forHash
andPred
satisfies theSwappable
requirements ]
After section 23.5.4.2 [unord.multimap.cnstr] add a new section and add the following paragraphs:
After section 23.5.6.2 [unord.set.cnstr] add a new section and add the following paragraphs:
After section 23.5.7.2 [unord.multiset.cnstr] add a new section and add the following paragraphs:
[ 2009-10-30 Pablo and Daniel updated wording. ]
[ 2010 Pittsburgh: Ready for Pittsburgh. ]
Proposed resolution:
[ This resolution is based on the September 2009 WP, N2960, except that it assumes that N2982 and issues 883(i) and 1232(i) have already been applied. Note in particular that Table 91 in N2960 is refered to as Table 90 because N2982 removed the old Table 90. This resolution also addresses issue 431(i). ]
In 23.2.2 [container.requirements.general], replace the a.swap(b) row in table 90, "container requirements" (was table 91 before the application of N2982 to the WP):
a.swap(b)
void
swap(a,b)(Note A)
Modify the notes immediately following Table 90 in 23.2.2 [container.requirements.general] as follows (The wording below is after the application of N2982 to N2960. The editor might also want to combine Notes A and B into one.):
Notes: the algorithms
swap(),equal() and lexicographical_compare() are defined in Clause 25. Those entries marked "(Note A)" or "(Note B)"shouldhave constant complexity .
In 23.2.2 [container.requirements.general], before paragraph 8, add:
[ Note to the editor: Paragraph 2 starts with a sentence fragment, clearly from an editing or source-control error. ]
Modify 23.2.7.2 [associative.reqmts.except] as follows:
23.2.4.1 Exception safety guarantees 23.2.7.2 [associative.reqmts.except]
For associative containers, no
clear()
function throws an exception.erase(k)
does not throw an exception unless that exception is thrown by the container'sobject (if any).
PredFor associative containers, if an exception is thrown by any operation from within an
insert()
function inserting a single element, theinsert()
function has no effect.For associative containers, no
swap
function throws an exception unless that exception is thrown by thecopy constructor or copy assignment operatorof the container'sobject (if any).
Pred
Modify 23.2.8.2 [unord.req.except], paragraph 3 as follows:
For unordered associative containers, no
swap
function throws an exception unless that exception is thrown by thecopy constructor or copy assignment operatorof the container'sHash
orPred
object (if any).
Modify section 23.3.3.4 [array.special]:
array specialized algorithms 23.3.3.4 [array.special]
template <class T, size_t N> void swap(array<T,N>& x,array<T,N>& y);
Effects:
swap_ranges(x.begin(), x.end(), y.begin() );
Add a new section after [array.fill] (Note to the editor: array::fill make use of a concept requirement that must be removed or changed to text.):
Insert a new paragraph just after 23.6 [container.adaptors]/1: