How to classify an NTTP class by creating a type trait?

Viewed 128

In C++20, NTTP extends new types which brings us the term structural:

  • l-value ref
  • integral
  • pointer, pointer to member, and null pointer
  • enumeration
  • floating point
  • A class in which: all base classes and non-static data members are public and non-mutable and the types of data members and base classes must also be structural recursively (I guess) and also the array.

From: https://en.cppreference.com/w/cpp/language/template_parameters

Here is a work around implementation that won't simply work:

template <auto>
struct nttp_test {};

template <typename T, typename = void>
struct is_structural : std::false_type {};

template <typename T>
struct is_structural<T, std::void_t<nttp_test<T{}>>> : std::true_type {};

template <typename T>
inline constexpr bool is_structural_v = is_structural<T>::value;

I'm not entirely sure if that works but I'm worried about the default initialization (I can't also use std::declval).

If it's impossible to implement, does it involve compiler magic?

2 Answers
template <auto>
struct nttp_test {};

template<class T> 
concept structural = requires { []<T x>(nttp_test<x>) { }; };

Demo.

One more C++20 construct could be of help here:

template<auto> class Meow {};

template<class T> concept meow = requires { typename Meow<T{}>; };

struct Nyan {};

int main() {
        std::cout << std::boolalpha << meow<int> << '\n';
        std::cout << std::boolalpha << meow<Nyan> << '\n';
        std::cout << std::boolalpha << meow<std::string> << '\n';
}

To convert a concept into a good old trait, well... template<class T> using is_meow = std::bool_constant<meow<T>>;.

Related