mirror of
https://gitlab.com/libeigen/eigen.git
synced 2026-04-10 11:34:33 +08:00
add SSE2 versions of sin, cos, log, exp using code from Julien
Pommier. They are for float only, and they return exactly the same result as the standard versions in about 90% of the cases. Otherwise the max error is below 1e-7. However, for very large values (>1e3) the accuracy of sin and cos slighlty decrease. They are about 3 or 4 times faster than 4 calls to their respective standard versions. So, is it ok to enable them by default in their respective functors ?
This commit is contained in:
@@ -34,6 +34,37 @@
|
||||
* of generic vectorized code.
|
||||
*/
|
||||
|
||||
struct ei_default_packet_traits
|
||||
{
|
||||
enum {
|
||||
HasAdd = 1,
|
||||
HasSub = 1,
|
||||
HasMul = 1,
|
||||
HasNegate = 1,
|
||||
HasAbs = 1,
|
||||
HasMin = 1,
|
||||
HasMax = 1,
|
||||
|
||||
HasDiv = 0,
|
||||
HasExp = 0,
|
||||
HasLog = 0,
|
||||
HasPow = 0,
|
||||
|
||||
HasSin = 0,
|
||||
HasCos = 0,
|
||||
HasTan = 0,
|
||||
HasASin = 0,
|
||||
HasACos = 0,
|
||||
HasATan = 0
|
||||
};
|
||||
};
|
||||
|
||||
template<typename T> struct ei_packet_traits : ei_default_packet_traits
|
||||
{
|
||||
typedef T type;
|
||||
enum {size=1};
|
||||
};
|
||||
|
||||
/** \internal \returns a + b (coeff-wise) */
|
||||
template<typename Packet> inline Packet
|
||||
ei_padd(const Packet& a,
|
||||
@@ -72,6 +103,22 @@ ei_pmax(const Packet& a,
|
||||
template<typename Packet> inline Packet
|
||||
ei_pabs(const Packet& a) { return ei_abs(a); }
|
||||
|
||||
/** \internal \returns the bitwise and of \a a and \a b */
|
||||
template<typename Packet> inline Packet
|
||||
ei_pand(const Packet& a, const Packet& b) { return a & b; }
|
||||
|
||||
/** \internal \returns the bitwise or of \a a and \a b */
|
||||
template<typename Packet> inline Packet
|
||||
ei_por(const Packet& a, const Packet& b) { return a | b; }
|
||||
|
||||
/** \internal \returns the bitwise xor of \a a and \a b */
|
||||
template<typename Packet> inline Packet
|
||||
ei_pxor(const Packet& a, const Packet& b) { return a ^ b; }
|
||||
|
||||
/** \internal \returns the bitwise andnot of \a a and \a b */
|
||||
template<typename Packet> inline Packet
|
||||
ei_pandnot(const Packet& a, const Packet& b) { return a & (!b); }
|
||||
|
||||
/** \internal \returns a packet version of \a *from, from must be 16 bytes aligned */
|
||||
template<typename Scalar> inline typename ei_packet_traits<Scalar>::type
|
||||
ei_pload(const Scalar* from) { return *from; }
|
||||
@@ -120,6 +167,22 @@ template<typename Packet> inline typename ei_unpacket_traits<Packet>::type ei_pr
|
||||
template<typename Packet> inline Packet ei_preverse(const Packet& a)
|
||||
{ return a; }
|
||||
|
||||
/**************************
|
||||
* Trnascendental functions
|
||||
***************************/
|
||||
|
||||
/** \internal \returns the sin of \a a (coeff-wise) */
|
||||
template<typename Packet> inline Packet ei_psin(const Packet& a) { return ei_sin(a); }
|
||||
|
||||
/** \internal \returns the cos of \a a (coeff-wise) */
|
||||
template<typename Packet> inline Packet ei_pcos(const Packet& a) { return ei_cos(a); }
|
||||
|
||||
/** \internal \returns the exp of \a a (coeff-wise) */
|
||||
template<typename Packet> inline Packet ei_pexp(const Packet& a) { return ei_exp(a); }
|
||||
|
||||
/** \internal \returns the log of \a a (coeff-wise) */
|
||||
template<typename Packet> inline Packet ei_plog(const Packet& a) { return ei_log(a); }
|
||||
|
||||
/***************************************************************************
|
||||
* The following functions might not have to be overwritten for vectorized types
|
||||
***************************************************************************/
|
||||
|
||||
Reference in New Issue
Block a user