std::aligned_storage
Defined in header <type_traits> | ||
template<std::size_t Len, std::size_t Align =/* default-alignment */> struct aligned_storage; | (since C++11) (deprecated in C++23) | |
Provides the nested type type
, which satisfies TrivialType and StandardLayoutType and suitable for use as uninitialized storage for any object whose size is at most Len
and whose alignment requirement is a divisor of Align
.
The default value of Align
is the most stringent (the largest) alignment requirement for any object whose size is at most Len
. If the default value is not used, Align
must be the value of alignof(T) for some type T
, or the behavior is undefined.
The behavior is undefined if Len ==0.
It is implementation-defined whether any extended alignment is supported.
If the program adds specializations for std::aligned_storage
, the behavior is undefined.
Contents |
[edit]Member types
Name | Definition |
type | a trivial and standard-layout type of at least size Len with alignment requirement Align |
[edit]Helper types
template<std::size_t Len, std::size_t Align =/* default-alignment */> using aligned_storage_t =typename aligned_storage<Len, Align>::type; | (since C++14) (deprecated in C++23) | |
[edit]Notes
The type defined by std::aligned_storage<>::type
can be used to create uninitialized memory blocks suitable to hold the objects of given type, optionally aligned stricter than their natural alignment requirement, for example on a cache or page boundary.
As with any other uninitialized storage, the objects are created using placement new and destroyed with explicit destructor calls.
[edit]Possible implementation
Except for default argument, aligned_storage is expressible in terms of alignas:
template<std::size_t Len, std::size_t Align =/* default alignment not implemented */>struct aligned_storage {struct type { alignas(Align)unsignedchar data[Len];};}; |
[edit]Example
A primitive static vector class, demonstrating creation, access, and destruction of objects in aligned storage.
#include <cstddef>#include <iostream>#include <new>#include <string>#include <type_traits> template<class T, std::size_t N>class static_vector {// Properly aligned uninitialized storage for N T's std::aligned_storage_t<sizeof(T), alignof(T)> data[N];std::size_t m_size =0; public:// Create an object in aligned storagetemplate<typename ...Args>void emplace_back(Args&&... args){if(m_size >= N)// Possible error handlingthrowstd::bad_alloc{}; // Construct value in memory of aligned storage using inplace operator new::new(&data[m_size]) T(std::forward<Args>(args)...);++m_size;} // Access an object in aligned storageconst T& operator[](std::size_t pos)const{// Note: std::launder is needed after the change of object model in P0137R1return*std::launder(reinterpret_cast<const T*>(&data[pos]));} // Destroy objects from aligned storage ~static_vector(){for(std::size_t pos =0; pos < m_size;++pos)// Note: std::launder is needed after the change of object model in P0137R1std::destroy_at(std::launder(reinterpret_cast<T*>(&data[pos])));}}; int main(){ static_vector<std::string, 10> v1; v1.emplace_back(5, '*'); v1.emplace_back(10, '*');std::cout<< v1[0]<<'\n'<< v1[1]<<'\n';}
Output:
***** **********
[edit]See also
alignas (C++11) | specifies that the storage for the variable should be aligned by specific amount (specifier) |
(C++11) | obtains the type's alignment requirements (class template) |
(C++17) | allocates aligned memory (function) |
(since C++11)(deprecated in C++23) | defines the type suitable for use as uninitialized storage for all given types (class template) |
(C++11) | trivial type with alignment requirement as great as any other scalar type (typedef) |
(C++17) | pointer optimization barrier (function template) |