|
8 | 8 |
|
9 | 9 | namespace ex = beman::execution26; |
10 | 10 |
|
11 | | -namespace |
12 | | -{ |
13 | | - template <std::size_t Size> |
14 | | - struct inline_resource |
15 | | - : std::pmr::memory_resource |
16 | | - { |
17 | | - char const* name; |
18 | | - inline_resource(char const* name): name(name) {} |
19 | | - std::byte buffer[Size]; |
20 | | - std::byte* next{+this->buffer}; |
| 11 | +namespace { |
| 12 | +template <std::size_t Size> |
| 13 | +struct inline_resource : std::pmr::memory_resource { |
| 14 | + const char* name; |
| 15 | + inline_resource(const char* name) : name(name) {} |
| 16 | + std::byte buffer[Size]; |
| 17 | + std::byte* next{+this->buffer}; |
21 | 18 |
|
22 | | - void* do_allocate(std::size_t size, std::size_t) override { |
23 | | - std::cout << "allocating from=" << this->name << ", size=" << size << "\n"; |
24 | | - if (size <= std::size_t(std::distance(next, std::end(buffer)))) { |
25 | | - std::byte* rc{this->next}; |
26 | | - this->next += size; |
27 | | - return rc; |
28 | | - } |
29 | | - return nullptr; |
| 19 | + void* do_allocate(std::size_t size, std::size_t) override { |
| 20 | + std::cout << "allocating from=" << this->name << ", size=" << size << "\n"; |
| 21 | + if (size <= std::size_t(std::distance(next, std::end(buffer)))) { |
| 22 | + std::byte* rc{this->next}; |
| 23 | + this->next += size; |
| 24 | + return rc; |
30 | 25 | } |
31 | | - void do_deallocate(void*, std::size_t, std::size_t) override { |
32 | | - } |
33 | | - bool do_is_equal(std::pmr::memory_resource const& other) const noexcept override { |
34 | | - return this == &other; |
35 | | - } |
36 | | - }; |
| 26 | + return nullptr; |
| 27 | + } |
| 28 | + void do_deallocate(void*, std::size_t, std::size_t) override {} |
| 29 | + bool do_is_equal(const std::pmr::memory_resource& other) const noexcept override { return this == &other; } |
| 30 | +}; |
37 | 31 |
|
38 | | - template <typename Fun> |
39 | | - struct allocator_aware_fun |
40 | | - { |
41 | | - using allocator_type = std::pmr::polymorphic_allocator<>; |
| 32 | +template <typename Fun> |
| 33 | +struct allocator_aware_fun { |
| 34 | + using allocator_type = std::pmr::polymorphic_allocator<>; |
42 | 35 |
|
43 | | - std::remove_cvref_t<Fun> fun; |
44 | | - allocator_type allocator{}; |
| 36 | + std::remove_cvref_t<Fun> fun; |
| 37 | + allocator_type allocator{}; |
45 | 38 |
|
46 | | - template <typename F> |
47 | | - requires std::same_as<std::remove_cvref_t<F>, std::remove_cvref_t<Fun>> |
48 | | - allocator_aware_fun(F&& fun): fun(std::forward<F>(fun)) {} |
49 | | - allocator_aware_fun(allocator_aware_fun const& other, allocator_type allocator = {}) |
50 | | - : fun(other.fun) |
51 | | - , allocator(allocator) |
52 | | - { |
53 | | - } |
54 | | - allocator_aware_fun(allocator_aware_fun&& other) |
55 | | - : fun(std::move(other.fun)) |
56 | | - , allocator(other.allocator) |
57 | | - { |
58 | | - } |
59 | | - allocator_aware_fun(allocator_aware_fun&& other, allocator_type allocator) |
60 | | - : fun(std::move(other.fun)) |
61 | | - , allocator(allocator) |
62 | | - { |
63 | | - } |
| 39 | + template <typename F> |
| 40 | + requires std::same_as<std::remove_cvref_t<F>, std::remove_cvref_t<Fun>> |
| 41 | + allocator_aware_fun(F&& fun) : fun(std::forward<F>(fun)) {} |
| 42 | + allocator_aware_fun(const allocator_aware_fun& other, allocator_type allocator = {}) |
| 43 | + : fun(other.fun), allocator(allocator) {} |
| 44 | + allocator_aware_fun(allocator_aware_fun&& other) : fun(std::move(other.fun)), allocator(other.allocator) {} |
| 45 | + allocator_aware_fun(allocator_aware_fun&& other, allocator_type allocator) |
| 46 | + : fun(std::move(other.fun)), allocator(allocator) {} |
64 | 47 |
|
65 | | - template <typename... Args> |
66 | | - auto operator()(Args&&... args) noexcept |
67 | | - { |
68 | | - return this->fun(this->allocator, std::forward<Args>(args)...); |
69 | | - } |
70 | | - }; |
71 | | - template <typename Fun> |
72 | | - allocator_aware_fun(Fun&& fun) -> allocator_aware_fun<Fun>; |
| 48 | + template <typename... Args> |
| 49 | + auto operator()(Args&&... args) noexcept { |
| 50 | + return this->fun(this->allocator, std::forward<Args>(args)...); |
| 51 | + } |
| 52 | +}; |
| 53 | +template <typename Fun> |
| 54 | +allocator_aware_fun(Fun&& fun) -> allocator_aware_fun<Fun>; |
73 | 55 |
|
74 | | - struct allocator_env |
75 | | - { |
76 | | - std::pmr::polymorphic_allocator<> allocator{}; |
77 | | - auto query(ex::get_allocator_t) const noexcept -> std::pmr::polymorphic_allocator<> { |
78 | | - return this->allocator; |
79 | | - } |
80 | | - }; |
81 | | -} |
| 56 | +struct allocator_env { |
| 57 | + std::pmr::polymorphic_allocator<> allocator{}; |
| 58 | + auto query(ex::get_allocator_t) const noexcept -> std::pmr::polymorphic_allocator<> { return this->allocator; } |
| 59 | +}; |
| 60 | +} // namespace |
82 | 61 |
|
83 | | -auto main() -> int |
84 | | -{ |
85 | | - int values[] = { 1, 2, 3 }; |
86 | | - auto s{ |
87 | | - ex::just(std::span(values)) |
88 | | - | ex::let_value(allocator_aware_fun([](auto alloc, std::span<int> v){ |
89 | | - return ex::just(std::pmr::vector<int>(v.begin(), v.end(), alloc)); |
90 | | - })) |
91 | | - | ex::then([](auto&& v) noexcept { |
92 | | - for (auto x: v){ std::cout << x << ", "; } |
93 | | - std::cout << "\n"; |
94 | | - }) |
95 | | - }; |
| 62 | +auto main() -> int { |
| 63 | + int values[] = {1, 2, 3}; |
| 64 | + auto s{ex::just(std::span(values)) | ex::let_value(allocator_aware_fun([](auto alloc, std::span<int> v) { |
| 65 | + return ex::just(std::pmr::vector<int>(v.begin(), v.end(), alloc)); |
| 66 | + })) | |
| 67 | + ex::then([](auto&& v) noexcept { |
| 68 | + for (auto x : v) { |
| 69 | + std::cout << x << ", "; |
| 70 | + } |
| 71 | + std::cout << "\n"; |
| 72 | + })}; |
96 | 73 |
|
97 | 74 | inline_resource<1024> state_resource("state"); |
98 | | - ex::sync_wait( |
99 | | - ex::detail::write_env(std::move(s), allocator_env{&state_resource}) |
100 | | - ); |
| 75 | + ex::sync_wait(ex::detail::write_env(std::move(s), allocator_env{&state_resource})); |
101 | 76 | } |
0 commit comments