[libcxx-commits] [libcxx] [libc++] Optimize copy construction and assignment of __tree (PR #151304)
Louis Dionne via libcxx-commits
libcxx-commits at lists.llvm.org
Thu Jul 31 06:38:44 PDT 2025
================
@@ -12,116 +12,93 @@
// map(const map& m, const allocator_type& a);
-#include <map>
#include <cassert>
+#include <map>
#include "test_macros.h"
#include "../../../test_compare.h"
#include "test_allocator.h"
#include "min_allocator.h"
-int main(int, char**) {
- {
- typedef std::pair<const int, double> V;
- V ar[] = {
- V(1, 1),
- V(1, 1.5),
- V(1, 2),
- V(2, 1),
- V(2, 1.5),
- V(2, 2),
- V(3, 1),
- V(3, 1.5),
- V(3, 2),
- };
- typedef test_less<int> C;
- typedef test_allocator<V> A;
- std::map<int, double, C, A> mo(ar, ar + sizeof(ar) / sizeof(ar[0]), C(5), A(7));
- std::map<int, double, C, A> m(mo, A(3));
- assert(m.get_allocator() == A(3));
- assert(m.key_comp() == C(5));
- assert(m.size() == 3);
- assert(std::distance(m.begin(), m.end()) == 3);
- assert(*m.begin() == V(1, 1));
- assert(*std::next(m.begin()) == V(2, 1));
- assert(*std::next(m.begin(), 2) == V(3, 1));
-
- assert(mo.get_allocator() == A(7));
- assert(mo.key_comp() == C(5));
- assert(mo.size() == 3);
- assert(std::distance(mo.begin(), mo.end()) == 3);
- assert(*mo.begin() == V(1, 1));
- assert(*std::next(mo.begin()) == V(2, 1));
- assert(*std::next(mo.begin(), 2) == V(3, 1));
+template <class Alloc>
+void test_alloc(const Alloc& new_alloc) {
+ { // Simple check
+ using V = std::pair<const int, int>;
+ V arr[] = {V(1, 1), V(2, 3), V(3, 6)};
+ std::map<int, int, std::less<int>, Alloc> orig(begin(arr), end(arr));
+ std::map<int, int, std::less<int>, Alloc> copy(orig, new_alloc);
+ assert(copy.size() == 3);
+ assert(*std::next(copy.begin(), 0) == V(1, 1));
+ assert(*std::next(copy.begin(), 1) == V(2, 3));
+ assert(*std::next(copy.begin(), 2) == V(3, 6));
+ assert(std::next(copy.begin(), 3) == copy.end());
+ assert(copy.get_allocator() == new_alloc);
+
+ // Check that orig is still what is expected
+ assert(orig.size() == 3);
+ assert(*std::next(orig.begin(), 0) == V(1, 1));
+ assert(*std::next(orig.begin(), 1) == V(2, 3));
+ assert(*std::next(orig.begin(), 2) == V(3, 6));
+ assert(std::next(orig.begin(), 3) == orig.end());
}
-#if TEST_STD_VER >= 11
- {
- typedef std::pair<const int, double> V;
- V ar[] = {
- V(1, 1),
- V(1, 1.5),
- V(1, 2),
- V(2, 1),
- V(2, 1.5),
- V(2, 2),
- V(3, 1),
- V(3, 1.5),
- V(3, 2),
- };
- typedef test_less<int> C;
- typedef min_allocator<V> A;
- std::map<int, double, C, A> mo(ar, ar + sizeof(ar) / sizeof(ar[0]), C(5), A());
- std::map<int, double, C, A> m(mo, A());
- assert(m.get_allocator() == A());
- assert(m.key_comp() == C(5));
- assert(m.size() == 3);
- assert(std::distance(m.begin(), m.end()) == 3);
- assert(*m.begin() == V(1, 1));
- assert(*std::next(m.begin()) == V(2, 1));
- assert(*std::next(m.begin(), 2) == V(3, 1));
-
- assert(mo.get_allocator() == A());
- assert(mo.key_comp() == C(5));
- assert(mo.size() == 3);
- assert(std::distance(mo.begin(), mo.end()) == 3);
- assert(*mo.begin() == V(1, 1));
- assert(*std::next(mo.begin()) == V(2, 1));
- assert(*std::next(mo.begin(), 2) == V(3, 1));
+
+ { // copy empty map
+ using V = std::pair<const int, int>;
+ std::map<int, int, std::less<int>, Alloc> orig;
+ std::map<int, int, std::less<int>, Alloc> copy = orig;
+ assert(copy.size() == 0);
+ assert(copy.begin() == copy.end());
+
+ // Check that orig is still what is expected
+ assert(orig.size() == 0);
+ assert(orig.begin() == orig.end());
+ }
+
+ { // only some leaf nodes exist
+ using V = std::pair<const int, int>;
+ V arr[] = {V(1, 1), V(2, 3), V(3, 6), V(4, 7), V(5, 0)};
+ std::map<int, int, std::less<int>, Alloc> orig(begin(arr), end(arr));
+ std::map<int, int, std::less<int>, Alloc> copy = orig;
+ assert(copy.size() == 5);
+ assert(*std::next(copy.begin(), 0) == V(1, 1));
+ assert(*std::next(copy.begin(), 1) == V(2, 3));
+ assert(*std::next(copy.begin(), 2) == V(3, 6));
+ assert(*std::next(copy.begin(), 3) == V(4, 7));
+ assert(*std::next(copy.begin(), 4) == V(5, 0));
+ assert(std::next(copy.begin(), 5) == copy.end());
+
+ // Check that orig is still what is expected
+ assert(orig.size() == 5);
+ assert(*std::next(orig.begin(), 0) == V(1, 1));
+ assert(*std::next(orig.begin(), 1) == V(2, 3));
+ assert(*std::next(orig.begin(), 2) == V(3, 6));
+ assert(*std::next(orig.begin(), 3) == V(4, 7));
+ assert(*std::next(orig.begin(), 4) == V(5, 0));
+ assert(std::next(orig.begin(), 5) == orig.end());
}
- {
- typedef std::pair<const int, double> V;
- V ar[] = {
- V(1, 1),
- V(1, 1.5),
- V(1, 2),
- V(2, 1),
- V(2, 1.5),
- V(2, 2),
- V(3, 1),
- V(3, 1.5),
- V(3, 2),
- };
- typedef test_less<int> C;
- typedef explicit_allocator<V> A;
- std::map<int, double, C, A> mo(ar, ar + sizeof(ar) / sizeof(ar[0]), C(5), A{});
- std::map<int, double, C, A> m(mo, A{});
- assert(m.get_allocator() == A());
- assert(m.key_comp() == C(5));
- assert(m.size() == 3);
- assert(std::distance(m.begin(), m.end()) == 3);
- assert(*m.begin() == V(1, 1));
- assert(*std::next(m.begin()) == V(2, 1));
- assert(*std::next(m.begin(), 2) == V(3, 1));
-
- assert(mo.get_allocator() == A());
- assert(mo.key_comp() == C(5));
- assert(mo.size() == 3);
- assert(std::distance(mo.begin(), mo.end()) == 3);
- assert(*mo.begin() == V(1, 1));
- assert(*std::next(mo.begin()) == V(2, 1));
- assert(*std::next(mo.begin(), 2) == V(3, 1));
+}
+
+void test() {
+ test_alloc(std::allocator<std::pair<const int, int>>());
+ test_alloc(test_allocator<std::pair<const int, int>>(25)); // Make sure that the new allocator is acutually used
----------------
ldionne wrote:
```suggestion
test_alloc(test_allocator<std::pair<const int, int>>(25)); // Make sure that the new allocator is actually used
```
https://github.com/llvm/llvm-project/pull/151304
More information about the libcxx-commits
mailing list