Date
2010-10-21.18:28:33
Message id
3493

Content

Proposed resolution:

Change [container.requirements.general]/4:

4 In Tables 91 and 92, X denotes a container class containing objects of type T, a and b denote values of type X, u denotes an identifier, r denotes an lvalue or a const rvalue a non-const value of type X, and rv denotes a non-const rvalue of type X.

Change the following rows in Table 91 — Container requirements [container.requirements.general]:

Table 91 — Container requirements
Expression Return type Assertion/note
pre-/post-condition
Complexity
X::value_type T Requires: T is Destructible. compile time

Change [container.requirements.general]/10:

Unless otherwise specified (see 23.2.4.1, 23.2.5.1, 23.3.2.3, and 23.3.6.4) all container types defined in this Clause meet the following additional requirements:

  • no erase(), clear(), pop_back() or pop_front() function throws an exception.

Insert a new paragraph prior to [container.requirements.general]/14:

The descriptions of the requirements of the type T in this section use the terms CopyConstructible, MoveConstructible, constructible from *i, and constructible from args. These terms are equivalent to the following expression using the appropriate arguments:


allocator_traits<allocator_type>::construct(x.get_allocator(), q, args...);

where x is a non-const lvalue of some container type X and q has type X::value_type*.

[Example: The container is going to move construct a T, so will call:


allocator_traits<allocator_type>::construct(get_allocator(), q, std::move(t));

The default implementation of construct will call:


::new (q) T(std::forward<T>(t)); // where forward is the same as move here, cast to rvalue

But the allocator author may override the above definition of construct and do the construction of T by some other means. — end example]

14 ...

Add to [container.requirements.general]/14:

14 In Table 93, X denotes an allocator-aware container class with a value_type of T using allocator of type A, u denotes a variable, a and b denote non-const lvalues of type X, t denotes an lvalue or a const rvalue of type X, rv denotes a non-const rvalue of type X, m is a value of type A, and Q is an allocator type.

Change or add the following rows in Table 93 — Allocator-aware container requirements in [container.requirements.general]:

Table 93 — Allocator-aware container requirements
Expression Return type Assertion/note
pre-/post-condition
Complexity
X(t, m)
X u(t, m);
Requires: T is CopyConstructible.
post: u == t,
get_allocator() == m
linear
X(rv, m)
X u(rv, m);
Requires: T is MoveConstructible.
post: u shall have the same elements, or copies of the elements, that rv had before this construction,
get_allocator() == m
constant if m == rv.get_allocator(), otherwise linear
a = t X& Requires: T is CopyConstructible and CopyAssignable
post: a == t.
linear
a = rv X& Requires: If allocator_traits< allocator_type > ::propagate_on_container_move_assignment ::value is false, T is MoveConstructible and MoveAssignable.
All existing elements of a are either move assigned to or destroyed.
a shall be equal to the value that rv had before this assignment
linear
a.swap(b); void exchanges the contents of a and b constant

Change the following rows in Table 94 — Sequence container requirements (in addition to container) in [sequence.reqmts]:

Table 94 — Sequence container requirements (in addition to container)
Expression Return type Assertion/note
pre-/post-condition
X(i, j)
X a(i, j)
Requires: If the iterator's dereference operation returns an lvalue or a const rvalue, T shall be CopyConstructible. T shall be constructible from *i.
If the iterator does not meet the forward iterator requirements ([forward.iterators]), then vector also requires T to be MoveConstructible.
Each iterator in the range [i,j) shall be dereferenced exactly once.
post: size() == distance between i and j
Constructs a sequence container equal to the range [i, j)
a = il; X& Requires: T is CopyConstructible and CopyAssignable.
a = X(il);
Assigns the range [il.begin(), il.end()) into a. All existing elements of a are either assigned or destroyed.
rReturns *this;
a.emplace(p, args); iterator Requires: ConstructibleAsElement<A, T, Args>. T is constructible from args. vector and deque also require T to be MoveConstructible and MoveAssignable. Inserts an object of type T constructed with std::forward<Args>(args)... before p.
a.insert(p, t); iterator Requires: ConstructibleAsElement<A, T, Args> and T shall be CopyAssignable. T shall be CopyConstructible. vector and deque also require T to be CopyAssignable. Inserts a copy t before p.
a.insert(p, rv); iterator Requires: ConstructibleAsElement<A, T, T&&> and T shall be MoveAssignable. T shall be MoveConstructible. vector and deque also require T to be MoveAssignable. Inserts a copy rv before p.
a.insert(p, i, j) iterator Requires: If the iterator's dereference operation returns an lvalue or a const rvalue, T shall be CopyConstructible. T shall be constructible from *i.
If the iterator does not meet the forward iterator requirements ([forward.iterators]), then vector also requires T to be MoveConstructible and MoveAssignable.
Each iterator in the range [i,j) shall be dereferenced exactly once.
pre: i and j are not iterators into a.
Inserts copies of elements in [i, j) before p
a.erase(q); iterator Requires: T and T shall be MoveAssignable. vector and deque require T to be MoveAssignable. Erases the element pointed to by q.
a.erase(q1, q2); iterator Requires: T and T shall be MoveAssignable. vector and deque require T to be MoveAssignable. Erases the elements in the range [q1, q2).
a.clear(); void erase(begin(), end())
Destroys all elements in a. Invalidates all references, pointers, and iterators referring to the elements of a and may invalidate the past-the-end iterator.
post: size() == 0 a.empty() == true
a.assign(i, j) void Requires: If the iterator's dereference operation returns an lvalue or a const rvalue, T shall be CopyConstructible and CopyAssignable. T shall be constructible and assignable from *i. If the iterator does not meet the forward iterator requirements ([forward.iterators]), then vector also requires T to be MoveConstructible.
Each iterator in the range [i,j) shall be dereferenced exactly once.
pre: i, j are not iterators into a.
Replaces elements in a with a copy of [i, j).

Change the following rows in Table 95 — Optional sequence container operations in [sequence.reqmts]:

Table 95 — Optional sequence container operations
Expression Return type Operational semantics Container
a.emplace_front(args) void a.emplace(a.begin(), std::forward<Args>(args)...)
Prepends an object of type T constructed with std::forward<Args>(args)....
Requires: ConstructibleAsElement<A, T, Args> T shall be constructible from args.
list, deque, forward_list
a.emplace_back(args) void a.emplace(a.end(), std::forward<Args>(args)...)
Appends an object of type T constructed with std::forward<Args>(args)....
Requires: ConstructibleAsElement<A, T, Args> T shall be constructible from args. vector also requires T to be MoveConstructible.
list, deque, vector
a.push_front(t) void a.insert(a.begin(), t)
Prepends a copy of t.
Requires: ConstructibleAsElement<A, T, T> and T shall be CopyAssignable. T shall be CopyConstructible.
list, deque, forward_list
a.push_front(rv) void a.insert(a.begin(), t)
Prepends a copy of rv.
Requires: ConstructibleAsElement<A, T, T&&> and T shall be MoveAssignable. T shall be MoveConstructible.
list, deque, forward_list
a.push_back(t) void a.insert(a.end(), t)
Appends a copy of t.
Requires: ConstructibleAsElement<A, T, T> and T shall be CopyAssignable. T shall be CopyConstructible.
vector, list, deque, basic_string
a.push_back(rv) void a.insert(a.end(), t)
Appends a copy of rv.
Requires: ConstructibleAsElement<A, T, T&&> and T shall be MoveAssignable. T shall be MoveConstructible.
vector, list, deque, basic_string
a.pop_front() void a.erase(a.begin())
Destroys the first element.
Requires: a.empty() shall be false.
list, deque, forward_list
a.pop_back() void { iterator tmp = a.end();
--tmp;
a.erase(tmp); }

Destroys the last element.
Requires: a.empty() shall be false.
vector, list, deque, basic_string

Insert a new paragraph prior to [associative.reqmts]/7, and edit paragraph 7:

The associative containers meet all of the requirements of Allocator-aware containers ([container.requirements.general]), except for the containers map and multimap, the requirements placed on value_type in Table 93 apply instead directly to key_type and mapped_type. [Note: For example key_type and mapped_type are sometimes required to be CopyAssignable even though the value_type (pair<const key_type, mapped_type>) is not CopyAssignable. — end note]

7 In Table 96, X denotes an associative container class, a denotes a value of X, a_uniq denotes a value of X when X supports unique keys, a_eq denotes a value of X when X supports multiple keys, u denotes an identifier, r denotes an lvalue or a const rvalue of type X, rv denotes a non-const rvalue of type X, i and j satisfy input iterator requirements and refer to elements implicitly convertible to value_type, [i,j) denotes a valid range, p denotes a valid const iterator to a, q denotes a valid dereferenceable const iterator to a, [q1, q2) denotes a valid range of const iterators in a, il designates an object of type initializer_list<value_type>, t denotes a value of X::value_type, k denotes a value of X::key_type and c denotes a value of type X::key_compare. A denotes the storage allocator used by X, if any, or std::allocator<X::value_type> otherwise, and m denotes an allocator of a type convertible to A.

Change or add the following rows in Table 96 — Associative container requirements (in addition to container) in [associative.reqmts]:

Table 96 — Associative container requirements (in addition to container)
Expression Return type Assertion/note
pre-/post-condition
Complexity
X::key_type Key Requires: Key is CopyConstructible and CopyAssignable Destructible compile time
X::mapped_type (map and multimap only) T Requires: T is Destructible compile time
X(c)
X a(c);
Requires: ConstructibleAsElement<A, key_compare, key_compare>.
key_compare is CopyConstructible.
Constructs an empty container.
Uses a copy of c as a comparison object.
constant
X()
X a;
Requires: ConstructibleAsElement<A, key_compare, key_compare>.
key_compare is DefaultConstructible.
Constructs an empty container.
Uses Compare() as a comparison object.
constant
X(i, j, c)
X a(i, j, c);
Requires: ConstructibleAsElement<A, key_compare, key_compare>.
key_compare is CopyConstructible. value_type shall be constructible from *i.
Constructs an empty container ans inserts elements from the range [i, j) into it; uses c as a comparison object.
N log N in general (N is the distance from i to j); linear if [i, j) is sorted with value_comp()
X(i, j)
X a(i, j);
Requires: ConstructibleAsElement<A, key_compare, key_compare>.
value_type shall be constructible from *i. key_compare is DefaultConstructible.
Same as above, but uses Compare() as a comparison object.
same as above
a = il X& a = X(il);
return *this;

Requires: T is CopyConstructible and CopyAssignable.
Assigns the range [il.begin(), il.end()) into a. All existing elements of a are either assigned or destroyed.
Same as a = X(il). N log N in general (N is il.size() added to the existing size of a); linear if [il.begin(), il.end()) is sorted with value_comp()
a_uniq.emplace(args) pair<iterator, bool> Requires: T shall be constructible from args
inserts a T object t constructed with std::forward<Args>(args)... if and only if there is no element in the container with key equivalent to the key of t. The bool component of the returned pair is true if and only if the insertion takes place, and the iterator component of the pair points to the element with key equivalent to the key of t.
logarithmic
a_eq.emplace(args) iterator Requires: T shall be constructible from args
inserts a T object t constructed with std::forward<Args>(args)... and returns the iterator pointing to the newly inserted element.
logarithmic
a_uniq.insert(t) pair<iterator, bool> Requires: T shall be MoveConstructible if t is a non-const rvalue expression, else T shall be CopyConstructible.
inserts t if and only if there is no element in the container with key equivalent to the key of t. The bool component of the returned pair is true if and only if the insertion takes place, and the iterator component of the pair points to the element with key equivalent to the key of t.
logarithmic
a_eq.insert(t) iterator Requires: T shall be MoveConstructible if t is a non-const rvalue expression, else T shall be CopyConstructible.
inserts t and returns the iterator pointing to the newly inserted element. If a range containing elements equivalent to t exists in a_eq, t is inserted at the end of that range.
logarithmic
a.insert(p, t) iterator Requires: T shall be MoveConstructible if t is a non-const rvalue expression, else T shall be CopyConstructible.
inserts t if and only if there is no element with key equivalent to the key of t in containers with unique keys; always inserts t in containers with equivalent keys; always returns the iterator pointing to the element with key equivalent to the key of t. t is inserted as close as possible to the position just prior to p.
logarithmic in general, but amortized constant if t is inserted right before p.
a.insert(i, j) void Requires: T shall be constructible from *i.
pre: i, j are not iterators into a. inserts each element from the range [i,j) if and only if there is no element with key equivalent to the key of that element in containers with unique keys; always inserts that element in containers with equivalent keys.
N log(size() + N ) (N is the distance from i to j)

Insert a new paragraph prior to [unord.req]/9:

The unordered associative containers meet all of the requirements of Allocator-aware containers ([container.requirements.general]), except for the containers unordered_map and unordered_multimap, the requirements placed on value_type in Table 93 apply instead directly to key_type and mapped_type. [Note: For example key_type and mapped_type are sometimes required to be CopyAssignable even though the value_type (pair<const key_type, mapped_type>) is not CopyAssignable. — end note]

9 ...

Change or add the following rows in Table 98 — Unordered associative container requirements (in addition to container) in [unord.req]:

Table 98 — Unordered associative container requirements (in addition to container)
Expression Return type Assertion/note
pre-/post-condition
Complexity
X::key_type Key Requires: Key shall be CopyAssignable and CopyConstructible Destructible compile time
X::mapped_type (unordered_map and unordered_multimap only) T Requires:T is Destructible compile time
X(n, hf, eq)
X a(n, hf, eq)
X Requires: hasher and key_equal are CopyConstructible. Constructs an empty container with at least n buckets, using hf as the hash function and eq as the key equality predicate. O(N)
X(n, hf)
X a(n, hf)
X Requires: hasher is CopyConstructible and key_equal is DefaultConstructible. Constructs an empty container with at least n buckets, using hf as the hash function and key_equal() as the key equality predicate. O(N)
X(n)
X a(n)
X Requires: hasher and key_equal are DefaultConstructible. Constructs an empty container with at least n buckets, using hasher() as the hash function and key_equal() as the key equality predicate. O(N)
X()
X a
X Requires: hasher and key_equal are DefaultConstructible. Constructs an empty container an unspecified number of buckets, using hasher() as the hash function and key_equal() as the key equality predicate. constant
X(i, j, n, hf, eq)
X a(i, j, n, hf, eq)
X Requires: value_type is constructible from *i. hasher and key_equal are CopyConstructible.
Constructs an empty container with at least n buckets, using hf as the hash function and eq as the key equality predicate, and inserts elements from [i, j) into it.
Average case O(N) (N is distance(i, j)), worst case O(N2)
X(i, j, n, hf)
X a(i, j, n, hf)
X Requires: value_type is constructible from *i. hasher is CopyConstructible and key_equal is DefaultConstructible.
Constructs an empty container with at least n buckets, using hf as the hash function and key_equal() as the key equality predicate, and inserts elements from [i, j) into it.
Average case O(N) (N is distance(i, j)), worst case O(N2)
X(i, j, n)
X a(i, j, n)
X Requires: value_type is constructible from *i. hasher and key_equal are DefaultConstructible.
Constructs an empty container with at least n buckets, using hasher() as the hash function and key_equal() as the key equality predicate, and inserts elements from [i, j) into it.
Average case O(N) (N is distance(i, j)), worst case O(N2)
X(i, j)
X a(i, j)
X Requires: value_type is constructible from *i. hasher and key_equal are DefaultConstructible.
Constructs an empty container with an unspecified number of buckets, using hasher() as the hash function and key_equal() as the key equality predicate, and inserts elements from [i, j) into it.
Average case O(N) (N is distance(i, j)), worst case O(N2)
X(b)
X a(b)
X Copy constructor. In addition to the contained elements requirements of Table 93 ([container.requirements.general]), copies the hash function, predicate, and maximum load factor. Average case linear in b.size(), worst case quadratic.
a = b X& Copy assignment operator. In addition to the contained elements requirements of Table 93 ([container.requirements.general]), copies the hash function, predicate, and maximum load factor. Average case linear in b.size(), worst case quadratic.
a = il X& a = X(il); return *this;
Requires: T is CopyConstructible and CopyAssignable.
Assigns the range [il.begin(), il.end()) into a. All existing elements of a are either assigned or destroyed.
Average case linear in il.size(), worst case quadratic.
a_uniq.emplace(args) pair<iterator, bool> Requires: T shall be constructible from args
inserts a T object t constructed with std::forward<Args>(args)... if and only if there is no element in the container with key equivalent to the key of t. The bool component of the returned pair is true if and only if the insertion takes place, and the iterator component of the pair points to the element with key equivalent to the key of t.
Average case O(1), worst case O(a_uniq.size()).
a_eq.emplace(args) iterator Requires: T shall be constructible from args
inserts a T object t constructed with std::forward<Args>(args)... and returns the iterator pointing to the newly inserted element.
Average case O(1), worst case O(a_eq.size()).
a.emplace_hint(p, args) iterator Requires: T shall be constructible from args
equivalent to a.emplace( std::forward<Args>(args)...). Return value is an iterator pointing to the element with the key equivalent to the newly inserted element. The const_iterator p is a hint pointing to where the search should start. Implementations are permitted to ignore the hint.
Average case O(1), worst case O(a.size()).
a_uniq.insert(t) pair<iterator, bool> Requires: T shall be MoveConstructible if t is a non-const rvalue expression, else T shall be CopyConstructible.
Inserts t if and only if there is no element in the container with key equivalent to the key of t. The bool component of the returned pair indicates whether the insertion takes place, and the iterator component points to the element with key equivalent to the key of t.
Average case O(1), worst case O(a_uniq.size()).
a_eq.insert(t) iterator Requires: T shall be MoveConstructible if t is a non-const rvalue expression, else T shall be CopyConstructible.
Inserts t, and returns an iterator pointing to the newly inserted element.
Average case O(1), worst case O(a_uniq.size()).
a.insert(q, t) iterator Requires: T shall be MoveConstructible if t is a non-const rvalue expression, else T shall be CopyConstructible.
Equivalent to a.insert(t). Return value is an iterator pointing to the element with the key equivalent to that of t. The iterator q is a hint pointing to where the search should start. Implementations are permitted to ignore the hint.
Average case O(1), worst case O(a_uniq.size()).
a.insert(i, j) void Requires: T shall be constructible from *i.
Pre: i and j are not iterators in a. Equivalent to a.insert(t) for each element in [i,j).
Average case O(N), where N is distance(i, j). Worst case O(N * a.size()).

Change [forwardlist]/2:

2 A forward_list satisfies all of the requirements of a container (table 91), except that the size() member function is not provided. A forward_list also satisfies all of the requirements of an allocator-aware container (table 93). And forward_list provides the assign member functions as specified in Table 94, Sequence container requirements, and several of the optional sequence container requirements (Table 95). Descriptions are provided here only for operations on forward_list that are not described in that table or for operations where there is additional semantic information.

Add a new paragraph after [forwardlist.modifiers]/23:

void clear();

23 Effects: Erases all elements in the range [begin(),end()).

Remarks: Does not invalidate past-the-end iterators.

Change [vector.capacity]/13:

void resize(size_type sz, const T& c);

13 Requires: T shall be CopyConstructible. If value_type has a move constructor, that constructor shall not throw any exceptions.

In [unord.set] and [unord.multiset] substitute "Key" for "Value".

The above substitution is normative as it ties into the requirements table.