Parcourir la source

C++ features: add cm::is_scoped_enum from C++23

Marc Chevrier il y a 9 mois
Parent
commit
a3ae58c9c5
2 fichiers modifiés avec 35 ajouts et 1 suppressions
  1. 5 0
      Help/dev/source.rst
  2. 30 1
      Utilities/std/cm/type_traits

+ 5 - 0
Help/dev/source.rst

@@ -221,6 +221,11 @@ Available features are:
   * ``<cm/vector>``:
     ``cm::erase``, ``cm::erase_if``, ``cm::ssize``
 
+* From ``C++23``:
+
+  * ``<cm/type_traits>``:
+    ``cm::is_scoped_enum``
+
 Additionally, some useful non-standard extensions to the C++ standard library
 are available in headers under the directory ``cmext/`` in namespace ``cm``.
 These are:

+ 30 - 1
Utilities/std/cm/type_traits

@@ -23,7 +23,7 @@ using enable_if_t = typename std::enable_if<B, T>::type;
 
 #endif
 
-#if __cplusplus >= 201703L || (defined(_MSVC_LANG) && _MSVC_LANG >= 201703)
+#if __cplusplus >= 201703L || (defined(_MSVC_LANG) && _MSVC_LANG >= 201703L)
 
 // Helper classes
 using std::bool_constant;
@@ -57,4 +57,33 @@ using void_t = typename make_void<ArgTypes...>::type;
 
 #endif
 
+#if (__cplusplus >= 202302L ||                                                \
+     (defined(_MSVC_LANG) && _MSVC_LANG >= 202302L)) &&                       \
+  __cpp_lib_is_scoped_enum == 202011L
+
+using std::is_scoped_enum;
+
+#else
+
+namespace internals {
+template <typename T, bool = std::is_enum<T>::value>
+struct is_scoped_enum_helper : std::false_type
+{
+};
+
+template <typename T>
+struct is_scoped_enum_helper<T, true>
+  : public cm::bool_constant<
+      !std::is_convertible<T, typename std::underlying_type<T>::type>::value>
+{
+};
+}
+
+template <typename T>
+struct is_scoped_enum : public internals::is_scoped_enum_helper<T>
+{
+};
+
+#endif
+
 } // namespace cm