C++1zから、アロケートする型を規定しないアロケータと、それを利用したメモリプールの仕組みが導入されます。
std::allocator<T>
クラスは型T
のオブジェクトをアロケートする機能を提供しますが、アロケートする型ごとにアロケータオブジェクトが必要になり、メモリリソースを共有することが難しい仕組みになっています。
C++1zの多相アロケータは、あらゆる型のオブジェクトをアロケートする基本的な仕組みとなります。
この目的のために<memory_resource>
ヘッダが新設され、大きく以下の2つのクラスが定義されます:
std::pmr::polymorphic_allocator
std::pmr::memory_resource
polymorphic_allocator
クラスは共有メモリリソースを使用するメモリアロケータ。memory_resource
クラスは共有メモリリソースの基本クラスになります。
memory_resource
から派生したクラスを共有メモリリソースとして使用できます。標準では<memory_resource>
ヘッダに、以下の3つのメモリリソースが定義されます。
std::pmr::synchronized_pool_resource
: スレッドセーフなメモリプールstd::pmr::unsynchronized_pool_resource
: スレッドセーフではないメモリプールstd::pmr::monotonic_buffer_resource
: 一度に全てを解放するような状況で使用する、高速なメモリアロケートを行う特殊なメモリリソース
また、多相アロケータとメモリリソースを扱いやすくするために、フリーストアを使用する標準の全てのコンテナに対して、polymorphic_allocator
を指定済みの別名がstd::pmr
名前空間に定義されます。これを使用してコードを書くと、以下のようになります。
#include <memory_resource> #include <vector> #include <string> int main() { // スレッドセーフなメモリプールを使用する std::pmr::synchronized_pool_resource mem_res; // vとsでメモリリソースを共有する std::pmr::vector<int> v(&mem_res); std::pmr::string s(&mem_res); }
polymorphic_allocator
クラスはmemory_resource
オブジェクトへのポインタをコンストラクタで受け取るので、コンテナにメモリリソースへのポインタを渡せば、polymorphic_allocator
にメモリリソースが伝搬されます。メモリリソースをコンテナに渡さない場合は、グローバルなデフォルトのメモリリソースが使用されます。デフォルトのメモリリソースは、std::pmr::set_default_resource()
関数で設定できます。
#include <memory_resource> #include <vector> #include <string> int main() { // スレッドセーフなメモリプールを // デフォルトのメモリリソースとして使用する std::pmr::synchronized_pool_resource mem_res; std::pmr::set_default_resource(&mem_res); // vとsでメモリリソースを共有する。 // デフォルトのメモリリソースを使用する std::pmr::vector<int> v; std::pmr::string s; }
最初のデフォルトメモリリソースとして何が使われるかは未規定です。
参照
- N3525 Polymorphic Allocators
- N3726 Polymorphic Memory Resources
- N3816 Polymorphic Memory Resources - r1
- N3916 Polymorphic Memory Resources - r2
- P0220R0 Adopt Library Fundamentals TS for C++17
- P0220R1 Adopt Library Fundamentals V1 TS Components for C++17 (R1)
- P0337R0 Delete
operator=
forpolymorphic_allocator
お断り
この記事の内容は、C++1zが正式リリースされる際には変更される可能性があります。正式リリース後には、C++日本語リファレンスサイトcpprefjpの以下の階層の下に解説ページを用意する予定です。