Utilities - Array helpers

A bunch of utility functions to move array data around, based on the
array elements' types.
This commit is contained in:
Emmanuel BENOîT 2018-12-15 20:42:39 +01:00
parent da2034c589
commit 71fee96926
2 changed files with 137 additions and 0 deletions

View file

@ -371,6 +371,35 @@ struct T_BigEndian
}; };
/*= ARRAY COPYING AND MOVING =================================================*/
template<
typename Type ,
bool IsTrivial = !std::is_class< Type >( )
> struct T_ArrayHelpers
{
// Default-initialise items in an array
static void init( Type* dest , const uint32_t size );
// Copy-initialise items in an array
static void init( Type* dest , const uint32_t size , Type const& value );
// Delete items in an array
static void destroy( Type* dest , const uint32_t size );
// Copy array items using copy constructors
static void copyNew( Type const* source , Type* dest , const uint32_t size );
// Copy array items using assignment operators
static void copyAssign( Type const* source , Type* dest , const uint32_t size );
// Initialise destination items using move constructors
static void moveNew( Type* source , Type* dest , const uint32_t size );
// Move items using assignments
static void moveAssign( Type* source , Type* dest , const uint32_t size );
// Move items using move constructors and delete source items
static void move( Type* source , Type* dest , const uint32_t size );
};
/*= COMPARATORS AND SORTING ==================================================*/ /*= COMPARATORS AND SORTING ==================================================*/
// F_Comparator< T > - T_Comparator function type // F_Comparator< T > - T_Comparator function type

View file

@ -152,6 +152,114 @@ struct T_BigEndian< T , E_Endian::BIG >
}; };
/*= ARRAY COPYING AND MOVING =================================================*/
// Array helpers for trivial types
template< typename T >
struct T_ArrayHelpers< T , true >
{
static void init( T* dest , const uint32_t size )
{ memset( dest , 0 , size * sizeof( T ) ); }
static void init( T* dest , const uint32_t size , T const& value )
{
for ( uint32_t i = 0 ; i < size ; i ++ ) {
::new ( reinterpret_cast< char* >( &dest[ i ] ) ) T( value );
}
}
static void destroy( T* dest , const uint32_t size )
{ M_UNUSED( dest ); M_UNUSED( size ); }
static void copyNew( T const* source , T* dest , const uint32_t size )
{ memmove( dest , source , sizeof( T ) * size ); }
static void copyAssign( T const* source , T* dest , const uint32_t size )
{ memmove( dest , source , sizeof( T ) * size ); }
static void moveNew( T* source , T* dest , const uint32_t size )
{ memmove( dest , source , sizeof( T ) * size ); }
static void moveAssign( T* source , T* dest , const uint32_t size )
{ memmove( dest , source , sizeof( T ) * size ); }
static void move( T* source , T* dest , const uint32_t size )
{ memmove( dest , source , sizeof( T ) * size ); }
};
/*----------------------------------------------------------------------------*/
// Array helpers for non-trivial types
template< typename T >
struct T_ArrayHelpers< T , false >
{
static void init( T* dest , const uint32_t size )
{
for ( uint32_t i = 0 ; i < size ; i ++ ) {
::new ( reinterpret_cast< char* >( &dest[ i ] ) ) T( );
}
}
static void init( T* dest , const uint32_t size , T const& value )
{
for ( uint32_t i = 0 ; i < size ; i ++ ) {
::new ( reinterpret_cast< char* >( &dest[ i ] ) ) T( value );
}
}
// ---------------------------------------------------------------------
static void destroy( T* dest , const uint32_t size )
{
for ( uint32_t i = 0 ; i < size ; i ++ ) {
dest[ i ].~T( );
}
}
// ---------------------------------------------------------------------
static void copyNew( T const* source , T* dest , const uint32_t size )
{
for ( uint32_t i = 0 ; i < size ; i ++ ) {
::new ( ( char* ) &( dest[ i ] ) ) T( source[ i ] );
}
}
static void copyAssign( T const* source , T* dest , const uint32_t size )
{
for ( uint32_t i = 0 ; i < size ; i ++ ) {
dest[ i ] = source[ i ];
}
}
// ---------------------------------------------------------------------
static void moveNew( T* source , T* dest , const uint32_t size )
{
for ( uint32_t i = 0 ; i < size ; i ++ ) {
::new ( reinterpret_cast< char* >( &( dest[ i ] ) ) )
T( std::move( source[ i ] ) );
}
}
static void moveAssign( T* source , T* dest , const uint32_t size )
{
for ( uint32_t i = 0 ; i < size ; i ++ ) {
dest[ i ] = std::move( source[ i ] );
}
}
static void move( T* source , T* dest , const uint32_t size )
{
for ( uint32_t i = 0 ; i < size ; i ++ ) {
::new ( reinterpret_cast< char* >( &( dest[ i ] ) ) )
T( std::move( source[ i ] ) );
source[ i ].~T( );
}
}
};
/*= COMPARATORS AND SORTING ==================================================*/ /*= COMPARATORS AND SORTING ==================================================*/
template< typename T > template< typename T >