The rules for emplace in map, multimap, unordered_map and unordered_multimap changed...
authorHoward Hinnant <hhinnant@apple.com>
Fri, 25 May 2012 22:04:21 +0000 (22:04 +0000)
committerHoward Hinnant <hhinnant@apple.com>
Fri, 25 May 2012 22:04:21 +0000 (22:04 +0000)
llvm-svn: 157503

libcxx/include/map
libcxx/include/unordered_map
libcxx/test/containers/associative/map/map.cons/default_recursive.pass.cpp
libcxx/test/containers/associative/map/map.modifiers/emplace.pass.cpp
libcxx/test/containers/associative/map/map.modifiers/emplace_hint.pass.cpp
libcxx/test/containers/associative/multimap/multimap.modifiers/emplace.pass.cpp
libcxx/test/containers/associative/multimap/multimap.modifiers/emplace_hint.pass.cpp
libcxx/test/containers/unord/unord.map/unorder.map.modifiers/emplace.pass.cpp
libcxx/test/containers/unord/unord.map/unorder.map.modifiers/emplace_hint.pass.cpp
libcxx/test/containers/unord/unord.multimap/unord.multimap.modifiers/emplace.pass.cpp
libcxx/test/containers/unord/unord.multimap/unord.multimap.modifiers/emplace_hint.pass.cpp

index 633579b..dd98da5 100644 (file)
@@ -880,45 +880,15 @@ public:
     value_compare  value_comp()    const {return value_compare(__tree_.value_comp().key_comp());}
 
 #ifndef _LIBCPP_HAS_NO_RVALUE_REFERENCES
-
-    _LIBCPP_INLINE_VISIBILITY
-    pair<iterator, bool>
-        emplace() {return __tree_.__emplace_unique();}
-
-    template <class _A0,
-              class = typename enable_if<is_constructible<value_type, _A0>::value>::type>
-        _LIBCPP_INLINE_VISIBILITY
-        pair<iterator, bool>
-        emplace(_A0&& __a0)
-            {return __tree_.__emplace_unique(_VSTD::forward<_A0>(__a0));}
-
 #ifndef _LIBCPP_HAS_NO_VARIADICS
 
-    template <class _A0, class ..._Args,
-              class = typename enable_if<is_constructible<key_type, _A0>::value>::type>
+    template <class ..._Args>
         pair<iterator, bool>
-        emplace(_A0&& __a0, _Args&& ...__args);
-
-#endif  // _LIBCPP_HAS_NO_VARIADICS
-
-    _LIBCPP_INLINE_VISIBILITY
-    iterator
-    emplace_hint(const_iterator __p)
-        {return __tree_.__emplace_hint_unique(__p.__i_);}
-
-    template <class _A0,
-              class = typename enable_if<is_constructible<value_type, _A0>::value>::type>
-        _LIBCPP_INLINE_VISIBILITY
-        iterator
-        emplace_hint(const_iterator __p, _A0&& __a0)
-            {return __tree_.__emplace_hint_unique(__p.__i_, _VSTD::forward<_A0>(__a0));}
-
-#ifndef _LIBCPP_HAS_NO_VARIADICS
+        emplace(_Args&& ...__args);
 
-    template <class _A0, class ..._Args,
-              class = typename enable_if<is_constructible<key_type, _A0>::value>::type>
+    template <class ..._Args>
         iterator
-        emplace_hint(const_iterator __p, _A0&& __a0, _Args&& ...__args);
+        emplace_hint(const_iterator __p, _Args&& ...__args);
 
 #endif  // _LIBCPP_HAS_NO_VARIADICS
 
@@ -1015,13 +985,23 @@ private:
 
 #ifndef _LIBCPP_HAS_NO_RVALUE_REFERENCES
     __node_holder __construct_node();
-    template <class _A0,
-              class = typename enable_if<is_constructible<value_type, _A0>::value>::type>
-        __node_holder __construct_node(_A0&& __a0);
+    template <class _A0>
+        typename enable_if
+        <
+            is_constructible<value_type, _A0>::value,
+            __node_holder
+        >::type
+         __construct_node(_A0&& __a0);
+    template <class _A0>
+        typename enable_if
+        <
+            is_constructible<key_type, _A0>::value,
+            __node_holder
+        >::type
+         __construct_node(_A0&& __a0);
 #ifndef _LIBCPP_HAS_NO_VARIADICS
-    template <class _A0, class ..._Args,
-              class = typename enable_if<is_constructible<key_type, _A0>::value>::type>
-        __node_holder __construct_node(_A0&& __a0, _Args&& ...__args);
+    template <class _A0, class _A1, class ..._Args>
+        __node_holder __construct_node(_A0&& __a0, _A1&& __a1, _Args&& ...__args);
 #endif  // _LIBCPP_HAS_NO_VARIADICS
 #else  // _LIBCPP_HAS_NO_RVALUE_REFERENCES
     __node_holder __construct_node(const key_type& __k);
@@ -1215,9 +1195,12 @@ map<_Key, _Tp, _Compare, _Allocator>::__construct_node()
 }
 
 template <class _Key, class _Tp, class _Compare, class _Allocator>
-template <class _A0,
-          class>
-typename map<_Key, _Tp, _Compare, _Allocator>::__node_holder
+template <class _A0>
+typename enable_if
+<
+    is_constructible<pair<const _Key, _Tp>, _A0>::value,
+    typename map<_Key, _Tp, _Compare, _Allocator>::__node_holder
+>::type
 map<_Key, _Tp, _Compare, _Allocator>::__construct_node(_A0&& __a0)
 {
     __node_allocator& __na = __tree_.__node_alloc();
@@ -1228,19 +1211,37 @@ map<_Key, _Tp, _Compare, _Allocator>::__construct_node(_A0&& __a0)
     return __h;
 }
 
+template <class _Key, class _Tp, class _Compare, class _Allocator>
+template <class _A0>
+typename enable_if
+<
+    is_constructible<_Key, _A0>::value,
+    typename map<_Key, _Tp, _Compare, _Allocator>::__node_holder
+>::type
+map<_Key, _Tp, _Compare, _Allocator>::__construct_node(_A0&& __a0)
+{
+    __node_allocator& __na = __tree_.__node_alloc();
+    __node_holder __h(__node_traits::allocate(__na, 1), _Dp(__na));
+    __node_traits::construct(__na, _VSTD::addressof(__h->__value_.first), _VSTD::forward<_A0>(__a0));
+    __h.get_deleter().__first_constructed = true;
+    __node_traits::construct(__na, _VSTD::addressof(__h->__value_.second));
+    __h.get_deleter().__second_constructed = true;
+    return __h;
+}
+
 #ifndef _LIBCPP_HAS_NO_VARIADICS
 
 template <class _Key, class _Tp, class _Compare, class _Allocator>
-template <class _A0, class ..._Args,
-          class>
+template <class _A0, class _A1, class ..._Args>
 typename map<_Key, _Tp, _Compare, _Allocator>::__node_holder
-map<_Key, _Tp, _Compare, _Allocator>::__construct_node(_A0&& __a0, _Args&& ...__args)
+map<_Key, _Tp, _Compare, _Allocator>::__construct_node(_A0&& __a0, _A1&& __a1, _Args&& ...__args)
 {
     __node_allocator& __na = __tree_.__node_alloc();
     __node_holder __h(__node_traits::allocate(__na, 1), _Dp(__na));
-    __node_traits::construct(__na, _VSTD::addressof(__h->__value_.first), _VSTD::forward<_A0>(__a0));
+    __node_traits::construct(__na, _VSTD::addressof(__h->__value_),
+                             _VSTD::forward<_A0>(__a0), _VSTD::forward<_A1>(__a1),
+                             _VSTD::forward<_Args>(__args)...);
     __h.get_deleter().__first_constructed = true;
-    __node_traits::construct(__na, _VSTD::addressof(__h->__value_.second), _VSTD::forward<_Args>(__args)...);
     __h.get_deleter().__second_constructed = true;
     return __h;
 }
@@ -1329,14 +1330,11 @@ map<_Key, _Tp, _Compare, _Allocator>::at(const key_type& __k) const
 #if !defined(_LIBCPP_HAS_NO_RVALUE_REFERENCES) && !defined(_LIBCPP_HAS_NO_VARIADICS)
 
 template <class _Key, class _Tp, class _Compare, class _Allocator>
-template <class _A0, class ..._Args,
-          class //= typename enable_if<is_constructible<_Key, _A0>::value>::type
-         >
+template <class ..._Args>
 pair<typename map<_Key, _Tp, _Compare, _Allocator>::iterator, bool>
-map<_Key, _Tp, _Compare, _Allocator>::emplace(_A0&& __a0, _Args&& ...__args)
+map<_Key, _Tp, _Compare, _Allocator>::emplace(_Args&& ...__args)
 {
-    __node_holder __h = __construct_node(_VSTD::forward<_A0>(__a0),
-                                         _VSTD::forward<_Args>(__args)...);
+    __node_holder __h = __construct_node(_VSTD::forward<_Args>(__args)...);
     pair<iterator, bool> __r = __tree_.__node_insert_unique(__h.get());
     if (__r.second)
         __h.release();
@@ -1344,15 +1342,12 @@ map<_Key, _Tp, _Compare, _Allocator>::emplace(_A0&& __a0, _Args&& ...__args)
 }
 
 template <class _Key, class _Tp, class _Compare, class _Allocator>
-template <class _A0, class ..._Args,
-          class //= typename enable_if<is_constructible<_Key, _A0>::value>::type
-         >
+template <class ..._Args>
 typename map<_Key, _Tp, _Compare, _Allocator>::iterator
 map<_Key, _Tp, _Compare, _Allocator>::emplace_hint(const_iterator __p,
-                                                   _A0&& __a0, _Args&& ...__args)
+                                                   _Args&& ...__args)
 {
-    __node_holder __h = __construct_node(_VSTD::forward<_A0>(__a0),
-                                         _VSTD::forward<_Args>(__args)...);
+    __node_holder __h = __construct_node(_VSTD::forward<_Args>(__args)...);
     iterator __r = __tree_.__node_insert_unique(__p.__i_, __h.get());
     if (__r.__i_.__ptr_ == __h.get())
         __h.release();
@@ -1629,43 +1624,15 @@ public:
         {return value_compare(__tree_.value_comp().key_comp());}
 
 #ifndef _LIBCPP_HAS_NO_RVALUE_REFERENCES
-
-    _LIBCPP_INLINE_VISIBILITY
-    iterator emplace() {return __tree_.__emplace_multi();}
-
-    template <class _A0,
-              class = typename enable_if<is_constructible<value_type, _A0>::value>::type>
-        _LIBCPP_INLINE_VISIBILITY
-        iterator
-        emplace(_A0&& __a0)
-            {return __tree_.__emplace_multi(_VSTD::forward<_A0>(__a0));}
-
 #ifndef _LIBCPP_HAS_NO_VARIADICS
 
-    template <class _A0, class ..._Args,
-              class = typename enable_if<is_constructible<key_type, _A0>::value>::type>
+    template <class ..._Args>
         iterator
-        emplace(_A0&& __a0, _Args&& ...__args);
-
-#endif  // _LIBCPP_HAS_NO_VARIADICS
+        emplace(_Args&& ...__args);
 
-    _LIBCPP_INLINE_VISIBILITY
-    iterator emplace_hint(const_iterator __p)
-        {return __tree_.__emplace_hint_multi(__p.__i_);}
-
-    template <class _A0,
-              class = typename enable_if<is_constructible<value_type, _A0>::value>::type>
-        _LIBCPP_INLINE_VISIBILITY
-        iterator
-        emplace_hint(const_iterator __p, _A0&& __a0)
-            {return __tree_.__emplace_hint_multi(__p.__i_, _VSTD::forward<_A0>(__a0));}
-
-#ifndef _LIBCPP_HAS_NO_VARIADICS
-
-    template <class _A0, class ..._Args,
-              class = typename enable_if<is_constructible<key_type, _A0>::value>::type>
+    template <class ..._Args>
         iterator
-        emplace_hint(const_iterator __p, _A0&& __a0, _Args&& ...__args);
+        emplace_hint(const_iterator __p, _Args&& ...__args);
 
 #endif  // _LIBCPP_HAS_NO_VARIADICS
 
@@ -1757,13 +1724,23 @@ private:
 
 #ifndef _LIBCPP_HAS_NO_RVALUE_REFERENCES
     __node_holder __construct_node();
-    template <class _A0,
-              class = typename enable_if<is_constructible<value_type, _A0>::value>::type>
-        __node_holder __construct_node(_A0&& __a0);
+    template <class _A0>
+        typename enable_if
+        <
+            is_constructible<value_type, _A0>::value,
+            __node_holder
+        >::type
+         __construct_node(_A0&& __a0);
+    template <class _A0>
+        typename enable_if
+        <
+            is_constructible<key_type, _A0>::value,
+            __node_holder
+        >::type
+         __construct_node(_A0&& __a0);
 #ifndef _LIBCPP_HAS_NO_VARIADICS
-    template <class _A0, class ..._Args,
-              class = typename enable_if<is_constructible<key_type, _A0>::value>::type>
-        __node_holder __construct_node(_A0&& __a0, _Args&& ...__args);
+    template <class _A0, class _A1, class ..._Args>
+        __node_holder __construct_node(_A0&& __a0, _A1&& __a1, _Args&& ...__args);
 #endif  // _LIBCPP_HAS_NO_VARIADICS
 #endif  // _LIBCPP_HAS_NO_RVALUE_REFERENCES
 };
@@ -1797,10 +1774,12 @@ multimap<_Key, _Tp, _Compare, _Allocator>::__construct_node()
 }
 
 template <class _Key, class _Tp, class _Compare, class _Allocator>
-template <class _A0,
-          class // = typename enable_if<is_constructible<value_type, _A0>::value>::type
-         >
-typename multimap<_Key, _Tp, _Compare, _Allocator>::__node_holder
+template <class _A0>
+typename enable_if
+<
+    is_constructible<pair<const _Key, _Tp>, _A0>::value,
+    typename multimap<_Key, _Tp, _Compare, _Allocator>::__node_holder
+>::type
 multimap<_Key, _Tp, _Compare, _Allocator>::__construct_node(_A0&& __a0)
 {
     __node_allocator& __na = __tree_.__node_alloc();
@@ -1811,20 +1790,37 @@ multimap<_Key, _Tp, _Compare, _Allocator>::__construct_node(_A0&& __a0)
     return __h;
 }
 
+template <class _Key, class _Tp, class _Compare, class _Allocator>
+template <class _A0>
+typename enable_if
+<
+    is_constructible<_Key, _A0>::value,
+    typename multimap<_Key, _Tp, _Compare, _Allocator>::__node_holder
+>::type
+multimap<_Key, _Tp, _Compare, _Allocator>::__construct_node(_A0&& __a0)
+{
+    __node_allocator& __na = __tree_.__node_alloc();
+    __node_holder __h(__node_traits::allocate(__na, 1), _Dp(__na));
+    __node_traits::construct(__na, _VSTD::addressof(__h->__value_.first), _VSTD::forward<_A0>(__a0));
+    __h.get_deleter().__first_constructed = true;
+    __node_traits::construct(__na, _VSTD::addressof(__h->__value_.second));
+    __h.get_deleter().__second_constructed = true;
+    return __h;
+}
+
 #ifndef _LIBCPP_HAS_NO_VARIADICS
 
 template <class _Key, class _Tp, class _Compare, class _Allocator>
-template <class _A0, class ..._Args,
-          class // = typename enable_if<is_constructible<key_type, _A0>::value>::type
-         >
+template <class _A0, class _A1, class ..._Args>
 typename multimap<_Key, _Tp, _Compare, _Allocator>::__node_holder
-multimap<_Key, _Tp, _Compare, _Allocator>::__construct_node(_A0&& __a0, _Args&& ...__args)
+multimap<_Key, _Tp, _Compare, _Allocator>::__construct_node(_A0&& __a0, _A1&& __a1, _Args&& ...__args)
 {
     __node_allocator& __na = __tree_.__node_alloc();
     __node_holder __h(__node_traits::allocate(__na, 1), _Dp(__na));
-    __node_traits::construct(__na, _VSTD::addressof(__h->__value_.first), _VSTD::forward<_A0>(__a0));
+    __node_traits::construct(__na, _VSTD::addressof(__h->__value_),
+                             _VSTD::forward<_A0>(__a0), _VSTD::forward<_A1>(__a1),
+                             _VSTD::forward<_Args>(__args)...);
     __h.get_deleter().__first_constructed = true;
-    __node_traits::construct(__na, _VSTD::addressof(__h->__value_.second), _VSTD::forward<_Args>(__args)...);
     __h.get_deleter().__second_constructed = true;
     return __h;
 }
@@ -1835,30 +1831,23 @@ multimap<_Key, _Tp, _Compare, _Allocator>::__construct_node(_A0&& __a0, _Args&&
 #if !defined(_LIBCPP_HAS_NO_RVALUE_REFERENCES) && !defined(_LIBCPP_HAS_NO_VARIADICS)
 
 template <class _Key, class _Tp, class _Compare, class _Allocator>
-template <class _A0, class ..._Args,
-          class //= typename enable_if<is_constructible<_Key, _A0>::value>::type
-         >
+template <class ..._Args>
 typename multimap<_Key, _Tp, _Compare, _Allocator>::iterator
-multimap<_Key, _Tp, _Compare, _Allocator>::emplace(_A0&& __a0, _Args&& ...__args)
+multimap<_Key, _Tp, _Compare, _Allocator>::emplace(_Args&& ...__args)
 {
-    __node_holder __h = __construct_node(_VSTD::forward<_A0>(__a0),
-                                         _VSTD::forward<_Args>(__args)...);
+    __node_holder __h = __construct_node(_VSTD::forward<_Args>(__args)...);
     iterator __r = __tree_.__node_insert_multi(__h.get());
     __h.release();
     return __r;
 }
 
 template <class _Key, class _Tp, class _Compare, class _Allocator>
-template <class _A0, class ..._Args,
-          class //= typename enable_if<is_constructible<_Key, _A0>::value>::type
-         >
+template <class ..._Args>
 typename multimap<_Key, _Tp, _Compare, _Allocator>::iterator
 multimap<_Key, _Tp, _Compare, _Allocator>::emplace_hint(const_iterator __p,
-                                                        _A0&& __a0,
                                                         _Args&& ...__args)
 {
-    __node_holder __h = __construct_node(_VSTD::forward<_A0>(__a0),
-                                         _VSTD::forward<_Args>(__args)...);
+    __node_holder __h = __construct_node(_VSTD::forward<_Args>(__args)...);
     iterator __r = __tree_.__node_insert_multi(__p.__i_, __h.get());
     __h.release();
     return __r;
index 15243f6..cb2ab42 100644 (file)
@@ -786,42 +786,15 @@ public:
     const_iterator cend()   const _NOEXCEPT {return __table_.end();}
 
 #ifndef _LIBCPP_HAS_NO_RVALUE_REFERENCES
-    _LIBCPP_INLINE_VISIBILITY
-    pair<iterator, bool> emplace()
-        {return __table_.__emplace_unique();}
-
-    template <class _A0,
-              class = typename enable_if<is_constructible<value_type, _A0>::value>::type>
-        _LIBCPP_INLINE_VISIBILITY
-        pair<iterator, bool> emplace(_A0&& __a0)
-            {return __table_.__emplace_unique(_VSTD::forward<_A0>(__a0));}
-
 #ifndef _LIBCPP_HAS_NO_VARIADICS
 
-    template <class _A0, class... _Args,
-              class = typename enable_if<is_constructible<key_type, _A0>::value>::type>
-        pair<iterator, bool> emplace(_A0&& __a0, _Args&&... __args);
-
-#endif  // _LIBCPP_HAS_NO_VARIADICS
-
-    _LIBCPP_INLINE_VISIBILITY
-    iterator emplace_hint(const_iterator)
-        {return __table_.__emplace_unique().first;}
+    template <class... _Args>
+        pair<iterator, bool> emplace(_Args&&... __args);
 
-    template <class _A0,
-              class = typename enable_if<is_constructible<value_type, _A0>::value>::type>
+    template <class... _Args>
         _LIBCPP_INLINE_VISIBILITY
-        iterator emplace_hint(const_iterator, _A0&& __a0)
-            {return __table_.__emplace_unique(_VSTD::forward<_A0>(__a0)).first;}
-
-#ifndef _LIBCPP_HAS_NO_VARIADICS
-
-    template <class _A0, class... _Args,
-              class = typename enable_if<is_constructible<key_type, _A0>::value>::type>
-        _LIBCPP_INLINE_VISIBILITY
-        iterator emplace_hint(const_iterator, _A0&& __a0, _Args&&... __args)
-            {return emplace(_VSTD::forward<_A0>(__a0),
-                            _VSTD::forward<_Args>(__args)...).first;}
+        iterator emplace_hint(const_iterator, _Args&&... __args)
+            {return emplace(_VSTD::forward<_Args>(__args)...).first;}
 #endif  // _LIBCPP_HAS_NO_VARIADICS
 #endif  // _LIBCPP_HAS_NO_RVALUE_REFERENCES
     _LIBCPP_INLINE_VISIBILITY
@@ -932,14 +905,25 @@ public:
 
 private:
 #ifndef _LIBCPP_HAS_NO_RVALUE_REFERENCES
+    __node_holder __construct_node();
+    template <class _A0>
+        typename enable_if
+        <
+            is_constructible<value_type, _A0>::value,
+            __node_holder
+        >::type
+         __construct_node(_A0&& __a0);
+    template <class _A0>
+        typename enable_if
+        <
+            is_constructible<key_type, _A0>::value,
+            __node_holder
+        >::type
+         __construct_node(_A0&& __a0);
 #ifndef _LIBCPP_HAS_NO_VARIADICS
-    template <class _A0, class... _Args,
-              class = typename enable_if<is_constructible<key_type, _A0>::value>::type>
-        __node_holder __construct_node(_A0&& __a0, _Args&&... __args);
+    template <class _A0, class _A1, class ..._Args>
+        __node_holder __construct_node(_A0&& __a0, _A1&& __a1, _Args&& ...__args);
 #endif  // _LIBCPP_HAS_NO_VARIADICS
-    template <class _A0,
-              class = typename enable_if<is_constructible<value_type, _A0>::value>::type>
-        __node_holder __construct_node(_A0&& __a0);
 #else  // _LIBCPP_HAS_NO_RVALUE_REFERENCES
     __node_holder __construct_node(const key_type& __k);
 #endif
@@ -1106,34 +1090,26 @@ unordered_map<_Key, _Tp, _Hash, _Pred, _Alloc>::operator=(
 #endif  // _LIBCPP_HAS_NO_GENERALIZED_INITIALIZERS
 
 #ifndef _LIBCPP_HAS_NO_RVALUE_REFERENCES
-#ifndef _LIBCPP_HAS_NO_VARIADICS
 
 template <class _Key, class _Tp, class _Hash, class _Pred, class _Alloc>
-template <class _A0, class... _Args,
-          class // = typename enable_if<is_constructible<key_type, _A0>::value>::type
-         >
 typename unordered_map<_Key, _Tp, _Hash, _Pred, _Alloc>::__node_holder
-unordered_map<_Key, _Tp, _Hash, _Pred, _Alloc>::__construct_node(_A0&& __a0,
-                                                                 _Args&&... __args)
+unordered_map<_Key, _Tp, _Hash, _Pred, _Alloc>::__construct_node()
 {
     __node_allocator& __na = __table_.__node_alloc();
     __node_holder __h(__node_traits::allocate(__na, 1), _Dp(__na));
-    __node_traits::construct(__na, _VSTD::addressof(__h->__value_.first),
-                             _VSTD::forward<_A0>(__a0));
+    __node_traits::construct(__na, _VSTD::addressof(__h->__value_));
     __h.get_deleter().__first_constructed = true;
-    __node_traits::construct(__na, _VSTD::addressof(__h->__value_.second),
-                             _VSTD::forward<_Args>(__args)...);
     __h.get_deleter().__second_constructed = true;
     return __h;
 }
 
-#endif  // _LIBCPP_HAS_NO_VARIADICS
-
 template <class _Key, class _Tp, class _Hash, class _Pred, class _Alloc>
-template <class _A0,
-          class // = typename enable_if<is_constructible<value_type, _A0>::value>::type
-         >
-typename unordered_map<_Key, _Tp, _Hash, _Pred, _Alloc>::__node_holder
+template <class _A0>
+typename enable_if
+<
+    is_constructible<pair<const _Key, _Tp>, _A0>::value,
+    typename unordered_map<_Key, _Tp, _Hash, _Pred, _Alloc>::__node_holder
+>::type
 unordered_map<_Key, _Tp, _Hash, _Pred, _Alloc>::__construct_node(_A0&& __a0)
 {
     __node_allocator& __na = __table_.__node_alloc();
@@ -1145,17 +1121,50 @@ unordered_map<_Key, _Tp, _Hash, _Pred, _Alloc>::__construct_node(_A0&& __a0)
     return __h;
 }
 
+template <class _Key, class _Tp, class _Hash, class _Pred, class _Alloc>
+template <class _A0>
+typename enable_if
+<
+    is_constructible<_Key, _A0>::value,
+    typename unordered_map<_Key, _Tp, _Hash, _Pred, _Alloc>::__node_holder
+>::type
+unordered_map<_Key, _Tp, _Hash, _Pred, _Alloc>::__construct_node(_A0&& __a0)
+{
+    __node_allocator& __na = __table_.__node_alloc();
+    __node_holder __h(__node_traits::allocate(__na, 1), _Dp(__na));
+    __node_traits::construct(__na, _VSTD::addressof(__h->__value_.first),
+                             _VSTD::forward<_A0>(__a0));
+    __h.get_deleter().__first_constructed = true;
+    __node_traits::construct(__na, _VSTD::addressof(__h->__value_.second));
+    __h.get_deleter().__second_constructed = true;
+    return __h;
+}
+
 #ifndef _LIBCPP_HAS_NO_VARIADICS
 
 template <class _Key, class _Tp, class _Hash, class _Pred, class _Alloc>
-template <class _A0, class... _Args,
-          class // = typename enable_if<is_constructible<key_type, _A0>::value>::type
-         >
+template <class _A0, class _A1, class ..._Args>
+typename unordered_map<_Key, _Tp, _Hash, _Pred, _Alloc>::__node_holder
+unordered_map<_Key, _Tp, _Hash, _Pred, _Alloc>::__construct_node(_A0&& __a0,
+                                                                 _A1&& __a1,
+                                                                 _Args&&... __args)
+{
+    __node_allocator& __na = __table_.__node_alloc();
+    __node_holder __h(__node_traits::allocate(__na, 1), _Dp(__na));
+    __node_traits::construct(__na, _VSTD::addressof(__h->__value_),
+                             _VSTD::forward<_A0>(__a0), _VSTD::forward<_A1>(__a1),
+                             _VSTD::forward<_Args>(__args)...);
+    __h.get_deleter().__first_constructed = true;
+    __h.get_deleter().__second_constructed = true;
+    return __h;
+}
+
+template <class _Key, class _Tp, class _Hash, class _Pred, class _Alloc>
+template <class... _Args>
 pair<typename unordered_map<_Key, _Tp, _Hash, _Pred, _Alloc>::iterator, bool>
-unordered_map<_Key, _Tp, _Hash, _Pred, _Alloc>::emplace(_A0&& __a0, _Args&&... __args)
+unordered_map<_Key, _Tp, _Hash, _Pred, _Alloc>::emplace(_Args&&... __args)
 {
-    __node_holder __h = __construct_node(_VSTD::forward<_A0>(__a0),
-                                         _VSTD::forward<_Args>(__args)...);
+    __node_holder __h = __construct_node(_VSTD::forward<_Args>(__args)...);
     pair<iterator, bool> __r = __table_.__node_insert_unique(__h.get());
     if (__r.second)
         __h.release();
@@ -1409,39 +1418,13 @@ public:
     const_iterator cend()   const _NOEXCEPT {return __table_.end();}
 
 #ifndef _LIBCPP_HAS_NO_RVALUE_REFERENCES
-    _LIBCPP_INLINE_VISIBILITY
-    iterator emplace()
-        {return __table_.__emplace_multi();}
-
-    template <class _A0,
-              class = typename enable_if<is_constructible<value_type, _A0>::value>::type>
-        _LIBCPP_INLINE_VISIBILITY
-        iterator emplace(_A0&& __a0)
-            {return __table_.__emplace_multi(_VSTD::forward<_A0>(__a0));}
-
 #ifndef _LIBCPP_HAS_NO_VARIADICS
 
-    template <class _A0, class... _Args,
-              class = typename enable_if<is_constructible<key_type, _A0>::value>::type>
-        iterator emplace(_A0&& __a0, _Args&&... __args);
+    template <class... _Args>
+        iterator emplace(_Args&&... __args);
 
-#endif  // _LIBCPP_HAS_NO_VARIADICS
-
-    _LIBCPP_INLINE_VISIBILITY
-    iterator emplace_hint(const_iterator __p)
-        {return __table_.__emplace_hint_multi(__p.__i_);}
-
-    template <class _A0,
-              class = typename enable_if<is_constructible<value_type, _A0>::value>::type>
-        _LIBCPP_INLINE_VISIBILITY
-        iterator emplace_hint(const_iterator __p, _A0&& __a0)
-            {return __table_.__emplace_hint_multi(__p.__i_, _VSTD::forward<_A0>(__a0));}
-
-#ifndef _LIBCPP_HAS_NO_VARIADICS
-
-    template <class _A0, class... _Args,
-              class = typename enable_if<is_constructible<key_type, _A0>::value>::type>
-        iterator emplace_hint(const_iterator __p, _A0&& __a0, _Args&&... __args);
+    template <class... _Args>
+        iterator emplace_hint(const_iterator __p, _Args&&... __args);
 #endif  // _LIBCPP_HAS_NO_VARIADICS
 #endif  // _LIBCPP_HAS_NO_RVALUE_REFERENCES
     _LIBCPP_INLINE_VISIBILITY
@@ -1543,14 +1526,27 @@ public:
     void reserve(size_type __n) {__table_.reserve(__n);}
 
 private:
-#if !defined(_LIBCPP_HAS_NO_RVALUE_REFERENCES) && !defined(_LIBCPP_HAS_NO_VARIADICS)
-    template <class _A0, class... _Args,
-              class = typename enable_if<is_constructible<key_type, _A0>::value>::type>
-        __node_holder __construct_node(_A0&& __a0, _Args&&... __args);
-    template <class _A0,
-              class = typename enable_if<is_constructible<value_type, _A0>::value>::type>
-        __node_holder __construct_node(_A0&& __a0);
-#endif  // !defined(_LIBCPP_HAS_NO_RVALUE_REFERENCES) && !defined(_LIBCPP_HAS_NO_VARIADICS)
+#ifndef _LIBCPP_HAS_NO_RVALUE_REFERENCES
+    __node_holder __construct_node();
+    template <class _A0>
+        typename enable_if
+        <
+            is_constructible<value_type, _A0>::value,
+            __node_holder
+        >::type
+         __construct_node(_A0&& __a0);
+    template <class _A0>
+        typename enable_if
+        <
+            is_constructible<key_type, _A0>::value,
+            __node_holder
+        >::type
+         __construct_node(_A0&& __a0);
+#ifndef _LIBCPP_HAS_NO_VARIADICS
+    template <class _A0, class _A1, class ..._Args>
+        __node_holder __construct_node(_A0&& __a0, _A1&& __a1, _Args&& ...__args);
+#endif  // _LIBCPP_HAS_NO_VARIADICS
+#endif  // _LIBCPP_HAS_NO_RVALUE_REFERENCES
 };
 
 template <class _Key, class _Tp, class _Hash, class _Pred, class _Alloc>
@@ -1716,34 +1712,26 @@ unordered_multimap<_Key, _Tp, _Hash, _Pred, _Alloc>::operator=(
 #endif  // _LIBCPP_HAS_NO_GENERALIZED_INITIALIZERS
 
 #ifndef _LIBCPP_HAS_NO_RVALUE_REFERENCES
-#ifndef _LIBCPP_HAS_NO_VARIADICS
 
 template <class _Key, class _Tp, class _Hash, class _Pred, class _Alloc>
-template <class _A0, class... _Args,
-          class // = typename enable_if<is_constructible<key_type, _A0>::value>::type
-         >
 typename unordered_multimap<_Key, _Tp, _Hash, _Pred, _Alloc>::__node_holder
-unordered_multimap<_Key, _Tp, _Hash, _Pred, _Alloc>::__construct_node(
-        _A0&& __a0, _Args&&... __args)
+unordered_multimap<_Key, _Tp, _Hash, _Pred, _Alloc>::__construct_node()
 {
     __node_allocator& __na = __table_.__node_alloc();
     __node_holder __h(__node_traits::allocate(__na, 1), _Dp(__na));
-    __node_traits::construct(__na, _VSTD::addressof(__h->__value_.first),
-                             _VSTD::forward<_A0>(__a0));
+    __node_traits::construct(__na, _VSTD::addressof(__h->__value_));
     __h.get_deleter().__first_constructed = true;
-    __node_traits::construct(__na, _VSTD::addressof(__h->__value_.second),
-                             _VSTD::forward<_Args>(__args)...);
     __h.get_deleter().__second_constructed = true;
     return __h;
 }
 
-#endif  // _LIBCPP_HAS_NO_VARIADICS
-
 template <class _Key, class _Tp, class _Hash, class _Pred, class _Alloc>
-template <class _A0,
-          class // = typename enable_if<is_constructible<value_type, _A0>::value>::type
-         >
-typename unordered_multimap<_Key, _Tp, _Hash, _Pred, _Alloc>::__node_holder
+template <class _A0>
+typename enable_if
+<
+    is_constructible<pair<const _Key, _Tp>, _A0>::value,
+    typename unordered_multimap<_Key, _Tp, _Hash, _Pred, _Alloc>::__node_holder
+>::type
 unordered_multimap<_Key, _Tp, _Hash, _Pred, _Alloc>::__construct_node(_A0&& __a0)
 {
     __node_allocator& __na = __table_.__node_alloc();
@@ -1755,32 +1743,61 @@ unordered_multimap<_Key, _Tp, _Hash, _Pred, _Alloc>::__construct_node(_A0&& __a0
     return __h;
 }
 
+template <class _Key, class _Tp, class _Hash, class _Pred, class _Alloc>
+template <class _A0>
+typename enable_if
+<
+    is_constructible<_Key, _A0>::value,
+    typename unordered_multimap<_Key, _Tp, _Hash, _Pred, _Alloc>::__node_holder
+>::type
+unordered_multimap<_Key, _Tp, _Hash, _Pred, _Alloc>::__construct_node(_A0&& __a0)
+{
+    __node_allocator& __na = __table_.__node_alloc();
+    __node_holder __h(__node_traits::allocate(__na, 1), _Dp(__na));
+    __node_traits::construct(__na, _VSTD::addressof(__h->__value_.first),
+                             _VSTD::forward<_A0>(__a0));
+    __h.get_deleter().__first_constructed = true;
+    __node_traits::construct(__na, _VSTD::addressof(__h->__value_.second));
+    __h.get_deleter().__second_constructed = true;
+    return __h;
+}
+
 #ifndef _LIBCPP_HAS_NO_VARIADICS
 
 template <class _Key, class _Tp, class _Hash, class _Pred, class _Alloc>
-template <class _A0, class... _Args,
-          class // = typename enable_if<is_constructible<key_type, _A0>::value>::type
-         >
+template <class _A0, class _A1, class ..._Args>
+typename unordered_multimap<_Key, _Tp, _Hash, _Pred, _Alloc>::__node_holder
+unordered_multimap<_Key, _Tp, _Hash, _Pred, _Alloc>::__construct_node(
+        _A0&& __a0, _A1&& __a1, _Args&&... __args)
+{
+    __node_allocator& __na = __table_.__node_alloc();
+    __node_holder __h(__node_traits::allocate(__na, 1), _Dp(__na));
+    __node_traits::construct(__na, _VSTD::addressof(__h->__value_),
+                             _VSTD::forward<_A0>(__a0), _VSTD::forward<_A1>(__a1),
+                             _VSTD::forward<_Args>(__args)...);
+    __h.get_deleter().__first_constructed = true;
+    __h.get_deleter().__second_constructed = true;
+    return __h;
+}
+
+template <class _Key, class _Tp, class _Hash, class _Pred, class _Alloc>
+template <class... _Args>
 typename unordered_multimap<_Key, _Tp, _Hash, _Pred, _Alloc>::iterator
-unordered_multimap<_Key, _Tp, _Hash, _Pred, _Alloc>::emplace(_A0&& __a0, _Args&&... __args)
+unordered_multimap<_Key, _Tp, _Hash, _Pred, _Alloc>::emplace(_Args&&... __args)
 {
-    __node_holder __h = __construct_node(_VSTD::forward<_A0>(__a0),
-                                         _VSTD::forward<_Args>(__args)...);
+    __node_holder __h = __construct_node(_VSTD::forward<_Args>(__args)...);
     iterator __r = __table_.__node_insert_multi(__h.get());
     __h.release();
     return __r;
 }
 
 template <class _Key, class _Tp, class _Hash, class _Pred, class _Alloc>
-template <class _A0, class... _Args,
-          class // = typename enable_if<is_constructible<key_type, _A0>::value>::type
-         >
+template <class... _Args>
 typename unordered_multimap<_Key, _Tp, _Hash, _Pred, _Alloc>::iterator
 unordered_multimap<_Key, _Tp, _Hash, _Pred, _Alloc>::emplace_hint(
-        const_iterator __p, _A0&& __a0, _Args&&... __args)
+        const_iterator __p, _Args&&... __args)
 {
-    __node_holder __h = __construct_node(_VSTD::forward<_A0>(__a0),
-                                         _VSTD::forward<_Args>(__args)...);
+    __node_holder __h = __construct_node(_VSTD::forward<_Args>(__args)...);
     iterator __r = __table_.__node_insert_multi(__p.__i_, __h.get());
     __h.release();
     return __r;
index e6380c7..4eb7e9f 100644 (file)
@@ -16,6 +16,7 @@
 
 #include <map>
 #include <cassert>
+#include <tuple>
 
 #include "../../../Emplaceable.h"
 #include "../../../DefaultOnly.h"
@@ -61,13 +62,15 @@ int main()
         assert(m.size() == 1);
         assert(m.begin()->first == 2);
         assert(m.begin()->second == Emplaceable());
-        r = m.emplace(1, 2, 3.5);
+        r = m.emplace(std::piecewise_construct, std::forward_as_tuple(1),
+                                                std::forward_as_tuple(2, 3.5));
         assert(r.second);
         assert(r.first == m.begin());
         assert(m.size() == 2);
         assert(m.begin()->first == 1);
         assert(m.begin()->second == Emplaceable(2, 3.5));
-        r = m.emplace(1, 2, 3.5);
+        r = m.emplace(std::piecewise_construct, std::forward_as_tuple(1),
+                                                std::forward_as_tuple(2, 3.5));
         assert(!r.second);
         assert(r.first == m.begin());
         assert(m.size() == 2);
index 115dffc..2bc225e 100644 (file)
@@ -57,12 +57,16 @@ int main()
         assert(m.size() == 1);
         assert(m.begin()->first == 2);
         assert(m.begin()->second == Emplaceable());
-        r = m.emplace_hint(m.end(), 1, 2, 3.5);
+        r = m.emplace_hint(m.end(), std::piecewise_construct, 
+                                    std::forward_as_tuple(1),
+                                    std::forward_as_tuple(2, 3.5));
         assert(r == m.begin());
         assert(m.size() == 2);
         assert(m.begin()->first == 1);
         assert(m.begin()->second == Emplaceable(2, 3.5));
-        r = m.emplace_hint(m.end(), 1, 2, 3.5);
+        r = m.emplace_hint(m.end(), std::piecewise_construct,
+                                    std::forward_as_tuple(1),
+                                    std::forward_as_tuple(2, 3.5));
         assert(r == m.begin());
         assert(m.size() == 2);
         assert(m.begin()->first == 1);
index 07f371a..22406d8 100644 (file)
@@ -57,12 +57,14 @@ int main()
         assert(m.size() == 1);
         assert(m.begin()->first == 2);
         assert(m.begin()->second == Emplaceable());
-        r = m.emplace(1, 2, 3.5);
+        r = m.emplace(std::piecewise_construct, std::forward_as_tuple(1),
+                                                std::forward_as_tuple(2, 3.5));
         assert(r == m.begin());
         assert(m.size() == 2);
         assert(m.begin()->first == 1);
         assert(m.begin()->second == Emplaceable(2, 3.5));
-        r = m.emplace(1, 3, 3.5);
+        r = m.emplace(std::piecewise_construct, std::forward_as_tuple(1),
+                                                std::forward_as_tuple(3, 3.5));
         assert(r == next(m.begin()));
         assert(m.size() == 3);
         assert(r->first == 1);
index 15c9e41..4c3e468 100644 (file)
@@ -57,12 +57,16 @@ int main()
         assert(m.size() == 1);
         assert(m.begin()->first == 2);
         assert(m.begin()->second == Emplaceable());
-        r = m.emplace_hint(m.cbegin(), 1, 2, 3.5);
+        r = m.emplace_hint(m.cbegin(), std::piecewise_construct,
+                                       std::forward_as_tuple(1),
+                                       std::forward_as_tuple(2, 3.5));
         assert(r == m.begin());
         assert(m.size() == 2);
         assert(m.begin()->first == 1);
         assert(m.begin()->second == Emplaceable(2, 3.5));
-        r = m.emplace_hint(m.cbegin(), 1, 3, 3.5);
+        r = m.emplace_hint(m.cbegin(), std::piecewise_construct,
+                                       std::forward_as_tuple(1),
+                                       std::forward_as_tuple(3, 3.5));
         assert(r == m.begin());
         assert(m.size() == 3);
         assert(r->first == 1);
index 66bb05e..488d2ba 100644 (file)
@@ -40,7 +40,8 @@ int main()
         assert(r.first->first == 4);
         assert(r.first->second == Emplaceable(5, 6));
 
-        r = c.emplace(5, 6, 7);
+        r = c.emplace(std::piecewise_construct, std::forward_as_tuple(5),
+                                               std::forward_as_tuple(6, 7));
         assert(r.second);
         assert(c.size() == 3);
         assert(r.first->first == 5);
index 41109d2..463fc3b 100644 (file)
@@ -39,7 +39,8 @@ int main()
         assert(r->first == 4);
         assert(r->second == Emplaceable(5, 6));
 
-        r = c.emplace_hint(e, 5, 6, 7);
+        r = c.emplace_hint(e, std::piecewise_construct, std::forward_as_tuple(5),
+                                                       std::forward_as_tuple(6, 7));
         assert(c.size() == 3);
         assert(r->first == 5);
         assert(r->second == Emplaceable(6, 7));
index 4b5fb60..f05edd8 100644 (file)
@@ -38,7 +38,8 @@ int main()
         assert(r->first == 4);
         assert(r->second == Emplaceable(5, 6));
 
-        r = c.emplace(5, 6, 7);
+        r = c.emplace(std::piecewise_construct, std::forward_as_tuple(5),
+                                                std::forward_as_tuple(6, 7));
         assert(c.size() == 3);
         assert(r->first == 5);
         assert(r->second == Emplaceable(6, 7));
index f2ca733..302451f 100644 (file)
@@ -40,7 +40,8 @@ int main()
         assert(r->second == Emplaceable(5, 6));
         assert(r == next(c.begin()));
 
-        r = c.emplace_hint(r, 3, 6, 7);
+        r = c.emplace_hint(r, std::piecewise_construct, std::forward_as_tuple(3),
+                                                        std::forward_as_tuple(6, 7));
         assert(c.size() == 3);
         assert(r->first == 3);
         assert(r->second == Emplaceable(6, 7));