From 011b7a5969abcca525d0fdd3d421908043485f89 Mon Sep 17 00:00:00 2001 From: Christian Mazakas Date: Mon, 1 May 2023 11:58:45 -0700 Subject: [PATCH] Add initial impl of clear --- .../boost/unordered/concurrent_flat_map.hpp | 2 + test/Jamfile.v2 | 1 + test/cfoa/clear_tests.cpp | 110 ++++++++++++++++++ 3 files changed, 113 insertions(+) create mode 100644 test/cfoa/clear_tests.cpp diff --git a/include/boost/unordered/concurrent_flat_map.hpp b/include/boost/unordered/concurrent_flat_map.hpp index c3cf5aeb..16809138 100644 --- a/include/boost/unordered/concurrent_flat_map.hpp +++ b/include/boost/unordered/concurrent_flat_map.hpp @@ -685,6 +685,8 @@ namespace boost { return table_.erase_if(f); } + void clear() noexcept { table_.clear(); } + /// Hash Policy /// void rehash(size_type n) { table_.rehash(n); } diff --git a/test/Jamfile.v2 b/test/Jamfile.v2 index d6038bdf..f3f6feb5 100644 --- a/test/Jamfile.v2 +++ b/test/Jamfile.v2 @@ -184,6 +184,7 @@ local CFOA_TESTS = visit_tests constructor_tests assign_tests + clear_tests ; for local test in $(CFOA_TESTS) diff --git a/test/cfoa/clear_tests.cpp b/test/cfoa/clear_tests.cpp new file mode 100644 index 00000000..12c0fc59 --- /dev/null +++ b/test/cfoa/clear_tests.cpp @@ -0,0 +1,110 @@ +// Copyright (C) 2023 Christian Mazakas +// Distributed under the Boost Software License, Version 1.0. (See accompanying +// file LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt) + +#include "helpers.hpp" + +#include + +test::seed_t initialize_seed{674140082}; + +using test::default_generator; +using test::limited_range; +using test::sequential; + +using hasher = stateful_hash; +using key_equal = stateful_key_equal; +using allocator_type = stateful_allocator >; + +using map_type = boost::unordered::concurrent_flat_map; + +using map_value_type = typename map_type::value_type; + +namespace { + template void clear_tests(G gen, test::random_generator rg) + { + auto values = make_random_values(1024 * 16, [&] { return gen(rg); }); + + raii::reset_counts(); + + map_type x(values.begin(), values.end(), values.size(), hasher(1), + key_equal(2), allocator_type(3)); + + BOOST_TEST_EQ(raii::copy_constructor, 2 * x.size()); + BOOST_TEST_EQ(raii::destructor, 0u); + + thread_runner(values, [&x](boost::span s) { + (void)s; + x.clear(); + }); + + BOOST_TEST(x.empty()); + + check_raii_counts(); + } + + template void insert_and_clear(G gen, test::random_generator rg) + { + auto values = make_random_values(1024 * 16, [&] { return gen(rg); }); + auto reference_map = + boost::unordered_flat_map(values.begin(), values.end()); + + raii::reset_counts(); + + std::thread t1, t2; + + { + map_type x(0, hasher(1), key_equal(2), allocator_type(3)); + + std::mutex m; + std::condition_variable cv; + + std::atomic done{false}; + + t1 = std::thread([&x, &values, &cv, &done] { + for (auto i = 0u; i < values.size(); ++i) { + x.insert(values[i]); + if (i % 100 == 0) { + cv.notify_all(); + } + } + done = true; + }); + + t2 = std::thread([&x, &m, &cv, &done] { + while (!done) { + { + std::unique_lock lk(m); + cv.wait(lk, [] { return true; }); + } + x.clear(); + } + }); + + t1.join(); + t2.join(); + + BOOST_TEST_LT(x.size(), reference_map.size()); + if (!x.empty()) { + test_fuzzy_matches_reference(x, reference_map, rg); + } + } + + check_raii_counts(); + } + +} // namespace + +// clang-format off +UNORDERED_TEST( + clear_tests, + ((value_type_generator)) + ((default_generator)(sequential)(limited_range))) + +UNORDERED_TEST(insert_and_clear, + ((value_type_generator)) + ((default_generator)(sequential)(limited_range))) +// clang-format on + +RUN_TESTS()