Info
-
Did you know that C++17 added std::pmr::polymorphic_allocator?
Example
#include <memory_resource>
#include <cassert>
int main() {
// Create a memory resource
std::pmr::monotonic_buffer_resource resource(1024);
// Create a polymorphic allocator using the memory resource
std::pmr::polymorphic_allocator<int> allocator(&resource);
// Allocate memory for an array of 10 integers using the polymorphic allocator
int* ptr = allocator.allocate(10);
// Test that the allocation was successful
assert(ptr);
// Deallocate the memory
allocator.deallocate(ptr, 10);
}
Puzzle
- Can you create pmr::vector which will use pmr::monotonic_buffer_resource/pmr::polymorphic_allocator?
#include <memory_resource>
#include <vector>
int main() {
using namespace boost::ut;
std::array<char, 1024> buffer{};
"pmr"_test = [&buffer] {
std::pmr::vector<char> vec{}; // TODO
vec.push_back('a');
vec.push_back('b');
vec.push_back('c');
expect(vec[0] == 'a' and vec[1] == 'b' and vec[2] == 'c');
expect(std::string_view(buffer.data(), buffer.size()).contains("abc"));
};
}
Solutions
int main() {
using namespace boost::ut;
std::array<char, 1024> buffer{};
"pmr"_test = [&buffer] {
std::pmr::monotonic_buffer_resource buf{buffer.data(), buffer.size()};
std::pmr::polymorphic_allocator<int> alloc{&buf};
std::pmr::vector<char> vec{alloc};
vec.push_back('a');
vec.push_back('b');
vec.push_back('c');
expect(vec[0] == 'a' and vec[1] == 'b' and vec[2] == 'c');
expect(std::string_view(buffer.data(), buffer.size()).contains("abc"));
};
}
int main() {
using namespace boost::ut;
std::array<char, 1024> buffer{};
"pmr"_test = [&buffer] {
std::pmr::monotonic_buffer_resource resource{std::data(buffer),
std::size(buffer)};
std::pmr::polymorphic_allocator<char> allocator{&resource};
std::pmr::vector<char> vec{allocator};
vec.push_back('a');
vec.push_back('b');
vec.push_back('c');
expect(vec[0] == 'a' and vec[1] == 'b' and vec[2] == 'c');
expect(std::string_view(buffer.data(), buffer.size()).contains("abc"));
};
}
int main() {
using namespace boost::ut;
std::array<char, 1024> buffer{};
std::pmr::monotonic_buffer_resource resource{buffer.data(), buffer.size()};
"pmr"_test = [&] {
std::pmr::vector<char> vec(&resource);
vec.push_back('a');
vec.push_back('b');
vec.push_back('c');
expect(vec[0] == 'a' and vec[1] == 'b' and vec[2] == 'c');
expect(std::string_view(buffer.data(), buffer.size()).contains("abc"));
};
}
int main() {
using namespace boost::ut;
std::array<char, 1024> buffer{};
"pmr"_test = [&buffer] {
// Create a memory resource
std::pmr::monotonic_buffer_resource resource{buffer.data(),
buffer.size()};
// Create a polymorphic allocator using the memory resource
std::pmr::polymorphic_allocator<char> allocator(&resource);
// std::vector<char, decltype(allocator)> vec{allocator};
std::pmr::vector<char> vec{allocator};
vec.push_back('a');
vec.push_back('b');
vec.push_back('c');
expect(vec[0] == 'a' and vec[1] == 'b' and vec[2] == 'c');
expect(std::string_view(buffer.data(), buffer.size()).contains("abc"));
};
}