diff --git a/alib2std/src/extensions/functional.hpp b/alib2std/src/extensions/functional.hpp index 28f616d73ebaf8808914abc27a33f34604a9701f..6c04581a39093118abf1e7ef7ed43c19eb02cde4 100644 --- a/alib2std/src/extensions/functional.hpp +++ b/alib2std/src/extensions/functional.hpp @@ -32,11 +32,29 @@ namespace ext { template < class T > -struct PolyComp { +class PolyComp { const T & m_inst; +public: explicit PolyComp ( const T & inst ) : m_inst ( inst ) { } + + template < class R > + friend bool operator < ( const PolyComp < T > & first, const R & second ) { + if constexpr ( supports < std::less < > ( T, R ) >::value ) + return first.m_inst < second; + else + return std::type_index ( typeid ( T ) ) < std::type_index ( typeid ( R ) ); + } + + template < class R > + friend bool operator < ( const R & first, const PolyComp < T > & second ) { + if constexpr ( supports < std::less < > ( R, T ) >::value ) + return first < second.m_inst; + else + return std::type_index ( typeid ( R ) ) < std::type_index ( typeid ( T ) ); + } + }; template < class T > @@ -44,44 +62,29 @@ PolyComp < T > poly_comp ( const T & inst ) { return PolyComp < T > ( inst ); } -template < class T, class R > -bool operator < ( const PolyComp < T > & first, const R & second ) { - if constexpr ( supports < std::less < > ( T, R ) >::value ) - return first.m_inst < second; - else - return std::type_index ( typeid ( T ) ) < std::type_index ( typeid ( R ) ); -} - -template < class R, class T > -bool operator < ( const R & first, const PolyComp < T > & second ) { - if constexpr ( supports < std::less < > ( R, T ) >::value ) - return first < second.m_inst; - else - return std::type_index ( typeid ( R ) ) < std::type_index ( typeid ( T ) ); -} - template < class ... Ts > -struct SliceComp { +class SliceComp { std::tuple < const Ts & ... > m_data; - explicit SliceComp ( const Ts & ... data ) : m_data ( data ... ) { - } - template < class T, size_t ... I > static bool compare ( const SliceComp < Ts ... > & first, const T & second, std::index_sequence < I ... > ) { return first.m_data < std::tie ( std::get < I > ( second ) ... ); } - template < class T > - friend bool operator < ( const SliceComp < Ts ... > & first, const T & second ) { - return compare < T > ( first, second, std::make_index_sequence < sizeof ... ( Ts ) > { } ); - } - template < class T, size_t ... I > static bool compare ( const T & first, const SliceComp < Ts ... > & second, std::index_sequence < I ... > ) { return std::tie ( std::get < I > ( first ) ... ) < second.m_data; } +public: + explicit SliceComp ( const Ts & ... data ) : m_data ( data ... ) { + } + + template < class T > + friend bool operator < ( const SliceComp < Ts ... > & first, const T & second ) { + return compare < T > ( first, second, std::make_index_sequence < sizeof ... ( Ts ) > { } ); + } + template < class T > friend bool operator < ( const T & first, const SliceComp < Ts ... > & second ) { return compare < T > ( first, second, std::make_index_sequence < sizeof ... ( Ts ) > { } );