qfloat16: make relational operators constexpr when QFLOAT16_IS_NATIVE
When qfloat16 uses float as an underlying type, the operators cannot be constexpr, because operator float() is not constexpr. However, operator NativeType() is, so we can make the relational operators constexpr when we are using a native 16-bit float as an underlying type. To avoid code duplication, introduce new temporary macros for constexpr and Q_DECLARE_PARTIALLY_ORDERED_LITERAL_TYPE. Extend the tests to verify that the operators are constexpr when native float16 type is used. Task-number: QTBUG-119433 Change-Id: I001b087d78c398c71b71a504b65c316199dd4792 Reviewed-by: Thiago Macieira <thiago.macieira@intel.com> Reviewed-by: Marc Mutz <marc.mutz@qt.io> (cherry picked from commit cfc385ce3fc674d48ea2bfbaac6d3f907795b1a5) Reviewed-by: Qt Cherry-pick Bot <cherrypick_bot@qt-project.org>
This commit is contained in:
parent
c112981789
commit
84fde7ef2f
@ -182,18 +182,28 @@ private:
|
||||
QT_WARNING_PUSH
|
||||
QT_WARNING_DISABLE_FLOAT_COMPARE
|
||||
|
||||
friend bool comparesEqual(const qfloat16 &lhs, const qfloat16 &rhs) noexcept
|
||||
#if QFLOAT16_IS_NATIVE
|
||||
# define QF16_CONSTEXPR constexpr
|
||||
# define QF16_PARTIALLY_ORDERED Q_DECLARE_PARTIALLY_ORDERED_LITERAL_TYPE
|
||||
#else
|
||||
# define QF16_CONSTEXPR
|
||||
# define QF16_PARTIALLY_ORDERED Q_DECLARE_PARTIALLY_ORDERED
|
||||
#endif
|
||||
|
||||
friend QF16_CONSTEXPR bool comparesEqual(const qfloat16 &lhs, const qfloat16 &rhs) noexcept
|
||||
{ return static_cast<NearestFloat>(lhs) == static_cast<NearestFloat>(rhs); }
|
||||
friend Qt::partial_ordering compareThreeWay(const qfloat16 &lhs, const qfloat16 &rhs) noexcept
|
||||
friend QF16_CONSTEXPR
|
||||
Qt::partial_ordering compareThreeWay(const qfloat16 &lhs, const qfloat16 &rhs) noexcept
|
||||
{ return Qt::compareThreeWay(static_cast<NearestFloat>(lhs), static_cast<NearestFloat>(rhs)); }
|
||||
Q_DECLARE_PARTIALLY_ORDERED(qfloat16)
|
||||
QF16_PARTIALLY_ORDERED(qfloat16)
|
||||
|
||||
#define QF16_MAKE_ORDER_OP_FP(FP) \
|
||||
friend bool comparesEqual(const qfloat16 &lhs, FP rhs) noexcept \
|
||||
friend QF16_CONSTEXPR bool comparesEqual(const qfloat16 &lhs, FP rhs) noexcept \
|
||||
{ return static_cast<FP>(lhs) == rhs; } \
|
||||
friend Qt::partial_ordering compareThreeWay(const qfloat16 &lhs, FP rhs) noexcept \
|
||||
friend QF16_CONSTEXPR \
|
||||
Qt::partial_ordering compareThreeWay(const qfloat16 &lhs, FP rhs) noexcept \
|
||||
{ return Qt::compareThreeWay(static_cast<FP>(lhs), rhs); } \
|
||||
Q_DECLARE_PARTIALLY_ORDERED(qfloat16, FP)
|
||||
QF16_PARTIALLY_ORDERED(qfloat16, FP)
|
||||
|
||||
QF16_MAKE_ORDER_OP_FP(long double)
|
||||
QF16_MAKE_ORDER_OP_FP(double)
|
||||
@ -204,27 +214,30 @@ QT_WARNING_DISABLE_FLOAT_COMPARE
|
||||
#undef QF16_MAKE_ORDER_OP_FP
|
||||
|
||||
template <typename T, if_type_is_integral<T> = true>
|
||||
friend bool comparesEqual(const qfloat16 &lhs, T rhs) noexcept
|
||||
friend QF16_CONSTEXPR bool comparesEqual(const qfloat16 &lhs, T rhs) noexcept
|
||||
{ return static_cast<NearestFloat>(lhs) == static_cast<NearestFloat>(rhs); }
|
||||
template <typename T, if_type_is_integral<T> = true>
|
||||
friend Qt::partial_ordering compareThreeWay(const qfloat16 &lhs, T rhs) noexcept
|
||||
friend QF16_CONSTEXPR Qt::partial_ordering compareThreeWay(const qfloat16 &lhs, T rhs) noexcept
|
||||
{ return Qt::compareThreeWay(static_cast<NearestFloat>(lhs), static_cast<NearestFloat>(rhs)); }
|
||||
|
||||
Q_DECLARE_PARTIALLY_ORDERED(qfloat16, qint8)
|
||||
Q_DECLARE_PARTIALLY_ORDERED(qfloat16, quint8)
|
||||
Q_DECLARE_PARTIALLY_ORDERED(qfloat16, qint16)
|
||||
Q_DECLARE_PARTIALLY_ORDERED(qfloat16, quint16)
|
||||
Q_DECLARE_PARTIALLY_ORDERED(qfloat16, qint32)
|
||||
Q_DECLARE_PARTIALLY_ORDERED(qfloat16, quint32)
|
||||
Q_DECLARE_PARTIALLY_ORDERED(qfloat16, long)
|
||||
Q_DECLARE_PARTIALLY_ORDERED(qfloat16, unsigned long)
|
||||
Q_DECLARE_PARTIALLY_ORDERED(qfloat16, qint64)
|
||||
Q_DECLARE_PARTIALLY_ORDERED(qfloat16, quint64)
|
||||
QF16_PARTIALLY_ORDERED(qfloat16, qint8)
|
||||
QF16_PARTIALLY_ORDERED(qfloat16, quint8)
|
||||
QF16_PARTIALLY_ORDERED(qfloat16, qint16)
|
||||
QF16_PARTIALLY_ORDERED(qfloat16, quint16)
|
||||
QF16_PARTIALLY_ORDERED(qfloat16, qint32)
|
||||
QF16_PARTIALLY_ORDERED(qfloat16, quint32)
|
||||
QF16_PARTIALLY_ORDERED(qfloat16, long)
|
||||
QF16_PARTIALLY_ORDERED(qfloat16, unsigned long)
|
||||
QF16_PARTIALLY_ORDERED(qfloat16, qint64)
|
||||
QF16_PARTIALLY_ORDERED(qfloat16, quint64)
|
||||
#ifdef QT_SUPPORTS_INT128
|
||||
Q_DECLARE_PARTIALLY_ORDERED(qfloat16, qint128)
|
||||
Q_DECLARE_PARTIALLY_ORDERED(qfloat16, quint128)
|
||||
QF16_PARTIALLY_ORDERED(qfloat16, qint128)
|
||||
QF16_PARTIALLY_ORDERED(qfloat16, quint128)
|
||||
#endif
|
||||
|
||||
#undef QF16_PARTIALLY_ORDERED
|
||||
#undef QF16_CONSTEXPR
|
||||
|
||||
QT_WARNING_POP
|
||||
|
||||
#ifndef QT_NO_DATASTREAM
|
||||
|
@ -21,6 +21,7 @@ class tst_qfloat16: public QObject
|
||||
|
||||
private slots:
|
||||
void compareCompiles();
|
||||
void relationalOperatorsAreConstexpr();
|
||||
void ordering_data();
|
||||
void ordering();
|
||||
void fuzzyCompare_data();
|
||||
@ -80,6 +81,45 @@ void tst_qfloat16::compareCompiles()
|
||||
#endif
|
||||
}
|
||||
|
||||
void tst_qfloat16::relationalOperatorsAreConstexpr()
|
||||
{
|
||||
#if QFLOAT16_IS_NATIVE
|
||||
|
||||
#define CHECK_CONSTEXPR(Type) \
|
||||
do { \
|
||||
constexpr qfloat16 lhs = qfloat16(0.0f); \
|
||||
constexpr Type rhs = 1; \
|
||||
static_assert(lhs < rhs); \
|
||||
static_assert(rhs >= lhs); \
|
||||
} while (false)
|
||||
|
||||
CHECK_CONSTEXPR(qfloat16);
|
||||
CHECK_CONSTEXPR(float);
|
||||
CHECK_CONSTEXPR(double);
|
||||
CHECK_CONSTEXPR(long double);
|
||||
CHECK_CONSTEXPR(qfloat16::NativeType);
|
||||
CHECK_CONSTEXPR(qint8);
|
||||
CHECK_CONSTEXPR(quint8);
|
||||
CHECK_CONSTEXPR(qint16);
|
||||
CHECK_CONSTEXPR(quint16);
|
||||
CHECK_CONSTEXPR(qint32);
|
||||
CHECK_CONSTEXPR(quint32);
|
||||
CHECK_CONSTEXPR(long);
|
||||
CHECK_CONSTEXPR(unsigned long);
|
||||
CHECK_CONSTEXPR(qint64);
|
||||
CHECK_CONSTEXPR(quint64);
|
||||
#ifdef QT_SUPPORTS_INT128
|
||||
CHECK_CONSTEXPR(qint128);
|
||||
CHECK_CONSTEXPR(quint128);
|
||||
#endif
|
||||
|
||||
#undef CHECK_CONSTEXPR
|
||||
|
||||
#else
|
||||
QSKIP("This check is only relevant for native float16 types");
|
||||
#endif // QFLOAT16_IS_NATIVE
|
||||
}
|
||||
|
||||
void tst_qfloat16::ordering_data()
|
||||
{
|
||||
QTest::addColumn<float>("left");
|
||||
|
Loading…
x
Reference in New Issue
Block a user