documented concurrent/unordered interop

This commit is contained in:
joaquintides
2023-07-23 12:23:08 +02:00
committed by Christian Mazakas
parent 6b6dde4f97
commit bf4a5efd2d
4 changed files with 61 additions and 0 deletions

View File

@ -10,6 +10,8 @@
* Added `[c]visit_while` operations to `boost::concurrent_map`,
with serial and parallel variants.
* Added efficient move construction of `boost::unordered_flat_map` from
`boost::concurrent_flat_map` and vice versa.
== Release 1.83.0 - Major update

View File

@ -201,3 +201,29 @@ and the user need not take any special precaution, but overall performance may b
Another blocking operation is _rehashing_, which happens explicitly via `rehash`/`reserve`
or during insertion when the table's load hits `max_load()`. As with non-concurrent containers,
reserving space in advance of bulk insertions will generally speed up the process.
== Interoperability with non-concurrent containers
As their internal data structure is basically the same, `boost::unordered_flat_map` can
be efficiently move-constructed from `boost::concurrent_flat_map` and vice versa.
This interoperability comes handy in multistage scenarios where parts of the data processing happen
in parallel whereas other steps are non-concurrent (or non-modifying). In the following example,
we want to construct a histogram from a huge input vector of words:
the population phase can be done in parallel with `boost::concurrent_flat_map` and results
then transferred to the final container.
[source,c++]
----
std::vector<std::string> words = ...;
// Insert words in parallel
boost::concurrent_flat_map<std::string_view, std::size_t> m0;
std::for_each(
std::execution::par, words.begin(), words.end(),
[&](const auto& word) {
m0.try_emplace_or_visit(word, 1, [](auto& x) { ++x.second; });
});
// Transfer to a regular unordered_flat_map
boost::unordered_flat_map m=std::move(m0);
----

View File

@ -69,6 +69,7 @@ namespace boost {
explicit xref:#concurrent_flat_map_allocator_constructor[concurrent_flat_map](const Allocator& a);
xref:#concurrent_flat_map_copy_constructor_with_allocator[concurrent_flat_map](const concurrent_flat_map& other, const Allocator& a);
xref:#concurrent_flat_map_move_constructor_with_allocator[concurrent_flat_map](concurrent_flat_map&& other, const Allocator& a);
xref:#concurrent_flat_map_move_constructor_from_unordered_flat_map[concurrent_flat_map](unordered_flat_map<Key, T, Hash, Pred, Allocator>&& other);
xref:#concurrent_flat_map_initializer_list_constructor[concurrent_flat_map](std::initializer_list<value_type> il,
size_type n = _implementation-defined_
const hasher& hf = hasher(),
@ -501,6 +502,21 @@ Concurrency:;; Blocking on `other`.
---
==== Move Constructor from unordered_flat_map
```c++
concurrent_flat_map(unordered_flat_map<Key, T, Hash, Pred, Allocator>&& other);
```
Move construction from a xref:#unordered_flat_map[`unordered_flat_map`].
The internal bucket array of `other` is transferred directly to the new container.
The hash function, predicate and allocator are moved-constructed from `other`.
[horizontal]
Complexity:;; O(`bucket_count()`)
---
==== Initializer List Constructor
[source,c++,subs="+quotes"]
----

View File

@ -77,6 +77,7 @@ namespace boost {
explicit xref:#unordered_flat_map_allocator_constructor[unordered_flat_map](const Allocator& a);
xref:#unordered_flat_map_copy_constructor_with_allocator[unordered_flat_map](const unordered_flat_map& other, const Allocator& a);
xref:#unordered_flat_map_move_constructor_with_allocator[unordered_flat_map](unordered_flat_map&& other, const Allocator& a);
xref:#unordered_flat_map_move_constructor_from_concurrent_flat_map[unordered_flat_map](concurrent_flat_map<Key, T, Hash, Pred, Allocator>&& other);
xref:#unordered_flat_map_initializer_list_constructor[unordered_flat_map](std::initializer_list<value_type> il,
size_type n = _implementation-defined_
const hasher& hf = hasher(),
@ -472,6 +473,22 @@ from `other`, and the allocator is copy-constructed from `a`.
---
==== Move Constructor from concurrent_flat_map
```c++
unordered_flat_map(concurrent_flat_map<Key, T, Hash, Pred, Allocator>&& other);
```
Move construction from a xref:#concurrent_flat_map[`concurrent_flat_map`].
The internal bucket array of `other` is transferred directly to the new container.
The hash function, predicate and allocator are moved-constructed from `other`.
[horizontal]
Complexity:;; Constant time.
Concurrency:;; Blocking on `other`.
---
==== Initializer List Constructor
[source,c++,subs="+quotes"]
----