density
C++11 library for paged memory management, function queues, heterogeneous queues and lifo memory management
|
#include <runtime_type.h>
Public Types | |
using | feature_list_type = typename std::conditional< (sizeof...(FEATURES) > 0), feature_list< FEATURES... >, default_type_features >::type |
using | tuple_type = typename feature_list_type::tuple_type |
Public Member Functions | |
constexpr | runtime_type () noexcept=default |
template<typename... OTHER_FEATURES> | |
constexpr | runtime_type (const runtime_type< OTHER_FEATURES... > &i_source) noexcept |
template<typename... OTHER_FEATURES> | |
DENSITY_CPP14_CONSTEXPR runtime_type & | operator= (const runtime_type< OTHER_FEATURES... > &i_source) noexcept |
constexpr bool | empty () const noexcept |
DENSITY_CPP14_CONSTEXPR void | clear () noexcept |
constexpr size_t | size () const noexcept |
constexpr size_t | alignment () const noexcept |
void | default_construct (void *i_dest) const |
void | copy_construct (void *i_dest, const void *i_source) const |
void | move_construct (void *i_dest, void *i_source) const |
void | destroy (void *i_dest) const noexcept |
const std::type_info & | type_info () const noexcept |
bool | are_equal (const void *i_first, const void *i_second) const noexcept |
template<typename FEATURE > | |
const FEATURE & | get_feature () const noexcept |
constexpr bool | operator== (const runtime_type &i_other) const noexcept |
constexpr bool | operator!= (const runtime_type &i_other) const noexcept |
template<typename TARGET_TYPE > | |
constexpr bool | is () const noexcept |
Static Public Member Functions | |
template<typename TARGET_TYPE > | |
static constexpr runtime_type | make () noexcept |
Friends | |
void | swap (runtime_type &i_first, runtime_type &i_second) noexcept |
Class template that performs type-erasure. A runtime_type can be empty, or can be bound to a target type, from which it captures and exposes the type features specified by the template argument list. It is copyable and trivially destructible. Specializations of runtime_type satisfy the requirements of RuntimeType.
FEATURES... | list of features to be captures from the target type. |
Implementation note: runtime_type is actually a wrapper around a pointer to a static constexpr instance of the tuple of the supported features. It is actually a generalization of the pointer to the v-table in a polymorphic type.
Like in a feature_list, each type in the template arguments pack is either:
Furthermore duplicate features are removed (only the first occurrence of a feature is considered). If after all these transformations two runtime_type specializations have the same feature_list, they are copyable and assignable each others:
This example shows a very simple usage of runtime_type:
Every type feature implies one or more concepts. For example f_equal implies EqualityComparable. If a target type does not satisfy the syntactic requirements of all the features supported by the runtime_type, the function make
fails to specialize, and a compile error is reported. For example we can't bind an instance of the RuntimeType
of the example above to std::lock_guard
, because RuntimeType
has the feature f_default_construct
, but std::lock_guard
is not default constructible.
Any type feature can be retrieved with the member function template get_feature
. Anyway a set of convenience member function is avaiable for the most common features: size, alignment, default_construct, copy_construct, move_construct, destroy, type_info, are_equal.
Managing instances of the target type directly is difficult and requires very low-level code: instances are handled by void pointers, they must explictly allocated, constructed, destroyed and deallocated. Indeed runtime_type is not intended to be used directly in this way, but it should instead used by library code to provide high-level features.
In the following example runtime_type is used to implement a class template very similar to std::any, which can be customized specifying which features must be captured from the underlying object.
This example shows how a non-intrusive serialization operator <<
for the above any
can be easly implemented exploiting the feature built-in f_ostream:
This example defines the feature f_sum
and then overloads the operator operator +
between two any
's
using feature_list_type = typename std::conditional< (sizeof...(FEATURES) > 0), feature_list<FEATURES...>, default_type_features>::type |
feature_list associated to the template arguments. If to template arguments is provided, default_type_features is used.
using tuple_type = typename feature_list_type::tuple_type |
Alias for feature_list_type::tuple_type
, a specialization of std::tuple that contains all the features.
Implementation note: runtime_type is actually a wrapper around a pointer to a static constexpr instance of this tuple.
|
defaultnoexcept |
Constructs an empty runtime_type not associated with any type. Trying to use any feature of an empty runtime_type leads to undefined behavior.
Postcoditions: Given a specialization of runtime_type R and type T, the following conditions hold:
Throws: nothing
|
inlinenoexcept |
Generalized copy constructor. This constructor does not participate in overload resolution unless runtime_type::tuple
and runtime_type<OTHER_FEATURES...>::tuple
are the same (that is the feature lists of the two runtime_type are equivalent).
Throws: nothing
|
inlinestaticnoexcept |
Creates a runtime_type bound to a target type.
TARGET_TYPE | type to bind to the returned runtime_type. |
Postcoditions: Given a specialization of runtime_type R and type T, the following conditions hold:
Throws: nothing
|
inlinenoexcept |
Generalized copy assignment. This function does not participate in overload resolution unless runtime_type::tuple
and runtime_type<OTHER_FEATURES...>::tuple
are the same (that is the feature lists of the two runtime_type are equivalent).
If the compiler conforms to C++14 (in particular __cpp_constexpr >= 201304
) this function is constexpr.
Throws: nothing
|
inlinenoexcept |
Returns whether this runtime_type is not bound to a target type.
Throws: nothing
|
inlinenoexcept |
Unbinds from a target. If the runtime_type was already empty this function has no effect.
If the compiler conforms to C++14 (in particular __cpp_constexpr >= 201304
) this function is constexpr.
Throws: nothing
|
inlinenoexcept |
Invokes the feature f_size and returns the size of the target type. Equivalent to get_feature<f_size>()()
.
The effect of this function is the same of this code:
Requires:
Precoditions: The behavior is undefined if any of these conditions is not satisfied:
Postcoditions:
Throws: nothing
|
inlinenoexcept |
Invokes the feature f_alignment and returns the alignment of the target type. Equivalent to get_feature<f_alignment>()()
.
The effect of this function is the same of this code:
Requires:
Precoditions: The behavior is undefined if any of these conditions is not satisfied:
Postcoditions:
Throws: nothing
|
inline |
Invokes the feature f_default_construct to value-initialize an instance of the target type. Equivalent to get_feature<f_default_construct>()(i_dest)
.
i_dest | pointer to the destination buffer in which the target type is in-place constructed. |
The effect of this function is the same of this code:
Note that if TARGET_TYPE is not a class type, it is zero-initialized.
Requires:
Precoditions: The behavior is undefined if any of these conditions is not satisfied:
Postcoditions:
Throws: anything that the constructor of the target type throws.
|
inline |
Invokes the feature f_copy_construct to copy-construct an instance of the target type. Equivalent to get_feature<f_copy_construct>()(i_dest, i_source)
.
i_dest | pointer to the destination buffer in which the target type is in-place constructed. |
i_source | pointer to an instance of the target type to be used as source for the copy. |
The effect of this function is the same of this code:
Requires:
Precoditions: The behavior is undefined if any of these conditions is not satisfied:
Postcoditions:
Throws: anything that the copy constructor of the target type throws.
|
inline |
Invokes the feature f_move_construct to move-construct an instance of the target type. Equivalent to get_feature<f_move_construct>()(i_dest, i_source)
.
i_dest | pointer to the destination buffer in which the target type is in-place constructed. |
i_source | pointer to an instance of the target type to be used as source for the move |
The effect of this function is the same of this code:
Requires:
Precoditions: The behavior is undefined if any of these conditions is not satisfied:
Postcoditions:
Throws: anything that the move constructor of the target type throws.
|
inlinenoexcept |
Invokes the feature f_destroy to destroy an instance of the target type. Equivalent to get_feature<f_destroy>()(i_dest)
.
i_dest | pointer to an instance of the target type to be destroyed. |
The effect of this function is the same of this code:
Requires:
Precoditions: The behavior is undefined if any of these conditions is not satisfied:
Postcoditions:
Throws: nothing.
|
inlinenoexcept |
Invokes the feature f_rtti to return the std::type_info of the target type. Equivalent to get_feature<f_rtti>()()
.
The effect of this function is the same of this code:
Precoditions: The behavior is undefined if any of these conditions is not satisfied:
Requires:
Throws: nothing.
|
inlinenoexcept |
Invokes the feature f_equal to compare two instances of the target type. Equivalent to get_feature<f_equal>()(i_first, i_second)
.
i_first | pointer to an instance of the target type |
i_second | pointer to an instance of the target type |
The effect of this function is the same of this code:
Requires:
Precoditions: The behavior is undefined if any of these conditions is not satisfied:
Throws: nothing.
|
inlinenoexcept |
Returns true whether this two runtime_type have the same target type. All empty runtime_type's compare equal.
Throws: nothing.
|
inlinenoexcept |
Returns true whether this two runtime_type have different target types. All empty runtime_type's compare equal.
Throws: nothing.
|
inlinenoexcept |
Returns whether the target type of this runtime_type is exactly the one specified in the template parameter. Equivalent to *this == runtime_type::make<TARGET_TYPE>()<&code>
Throws: nothing.
|
friend |