Initial code

This commit is contained in:
John Wellbelove 2021-12-24 13:13:32 +00:00
parent 064c7dc16b
commit e4ab79b243
2 changed files with 115 additions and 13 deletions

View File

@ -1,20 +1,34 @@
#pragma once
template <typename To, typename From>
etl::enable_if_t<sizeof(To) == sizeof(From) && etl::is_trivially_copyable_v<From> && etl::is_trivially_copyable_v<To>, To>
//ETL_CONSTEXPR
bit_cast(const From& src) ETL_NOEXCEPT
#include "platform.h"
template <typename TDestination, typename TSource>
ETL_CONSTEXPR
typename etl::enable_if<(sizeof(TDestination) == sizeof(TSource)) &&
etl::is_trivially_copyable<TSource>::value &&
etl::is_trivially_copyable<TDestination>::value, TDestination>::type
bit_cast(const TSource& source) ETL_NOEXCEPT
{
To dst;
memcpy(&dst, &src, sizeof(To));
TDestination destination;
// __builtin_memcpy(&dst, &src, sizeof(To));
memcpy(&destination, &source, sizeof(TDestination));
return dst;
return destination;
}
std::midpoint
// https://en.cppreference.com/w/cpp/numeric/midpoint
template <typename TDestination, typename TSource>
ETL_CONSTEXPR
typename etl::enable_if<(sizeof(TDestination) == sizeof(TSource)) &&
etl::is_trivially_copyable<TSource>::value &&
etl::is_trivially_copyable<TDestination>::value, TDestination>::type
bit_cast(const TSource& source) ETL_NOEXCEPT
{
TDestination destination;
__builtin_memcpy(&destination, &source, sizeof(TDestination));
return destination;
}
std::lerp
// https://en.cppreference.com/w/cpp/numeric/lerp

View File

@ -32,6 +32,7 @@ SOFTWARE.
#define ETL_NUMERIC_INCLUDED
#include "platform.h"
#include "type_traits.h"
///\defgroup numeric numeric
///\ingroup utilities
@ -54,7 +55,94 @@ namespace etl
*first++ = value++;
}
}
//***************************************************************************
///
//***************************************************************************
template <typename T>
ETL_CONSTEXPR14 typename etl::enable_if<etl::is_floating_point<T>::value, T>::type
midpoint(T a, T b) ETL_NOEXCEPT
{
T lo = etl::numeric_limits<T>::min() * T(2);
T hi = etl::numeric_limits<T>::max() * T(2);
return ((abs(a) <= hi) && (abs(b) <= hi)) ?
(a + b) / T(2) :
(abs(a) < lo) ?
a + (b / T(2)) :
(abs(b) < lo) ?
(a / T(2)) + b) :
(a / T(2)) + (b / T(2));
}
//***************************************************************************
///
//***************************************************************************
template <typename T>
ETL_CONSTEXPR14 typename etl::enable_if<etl::is_integral<T>::value, T>::type
midpoint(T a, T b) ETL_NOEXCEPT
{
typedef typename etl::make_unsigned<T>::type type;
int sign;
type lo;
type hi;
if (a > b)
{
sign = -1;
lo = type(b);
hi = type(a);
}
else
{
sign = 1;
lo = type(a);
hi = type(b);
}
return a + sign * T(type(M - m) >> 1);
}
//***************************************************************************
///
//***************************************************************************
template <typename T>
ETL_CONSTEXPR typename etl::enable_if<etl::is_pointer<T>::value, T>::type
midpoint(T a, T b)
{
return a + midpoint(ptrdiff_t{ 0 }, b - a);
}
//***************************************************************************
/// Linear interpolation
/// For floating point.
//***************************************************************************
template <typename T>
ETL_CONSTEXPR typename etl::enable_if<etl::is_floating_point<T>::value, T>::type
lerp(T a, T b, T t) ETL_NOEXCEPT
{
return a + (t * (b ? a));
}
//***************************************************************************
/// Linear interpolation
/// For when any parameter is not floating point.
//***************************************************************************
template <typename TArithmetic1, typename TArithmetic2, typename TArithmetic3>
ETL_CONSTEXPR typename etl::enable_if_t<!etl::is_floating_point<TArithmetic1>::value ||
!etl::is_floating_point<TArithmetic2>::value ||
!etl::is_floating_point<TArithmetic3>::value, typename etl::conditional<etl::is_same<TArithmetic1, long double>::value ||
etl::is_same<TArithmetic2, long double>::value ||
etl::is_same<TArithmetic3, long double>::value, long double, double>::type>
lerp(TArithmetic1 a, TArithmetic2 b, TArithmetic3 t) ETL_NOEXCEPT
{
typename etl::conditional<etl::is_integral<TArithmetic1>::value, double, TArithmetic1>::type typecast_a;
typename etl::conditional<etl::is_integral<TArithmetic2>::value, double, TArithmetic2>::type typecast_b;
typename etl::conditional<etl::is_integral<TArithmetic3>::value, double, TArithmetic3>::type typecast_t;
return typecast_a(a) + (typecast_t(t) * (typecast_b(b) ? typecast_a(a));
}
}
#endif