I have already knew that concept is a compile-time predicate which can constrain templates or auto
.
I have discovered that the concepts will return the prvalue of type bool
, so I could print it to test myself.
I also read this specific question Can concepts(C++20) be used as a boolean? and the answer which clarifies the concepts that can be used as boolean values.
[temp.names] (8) A concept-id is a simple-template-id where the template-name is a concept-name. A concept-id is a prvalue of type bool, and does not name a template specialization. A concept-id evaluates to true if the concept's normalized constraint-expression is satisfied ([temp.constr.constr]) by the specified template arguments and false otherwise.
For example:
template <typename T>
concept meowable = requires (T obj) {
{ obj.meow() } -> std::same_as<T&>;
};
struct Dog {};
struct Cat { Cat& meow(); };
struct Wolf { Wolf& woof(); };
Application:
std::cout << std::boolalpha;
std::cout << "Has meow?" << '\n'
<< "Dog: " << meowable<Dog> << '\n'
<< "Cat: " << meowable<Cat> << '\n'
<< "Wolf: " << meowable<Wolf> << '\n';
Output:
Has meow?
Dog: false
Cat: true
Wolf: false
I could also create type trait out of concepts:
template <typename T>
struct has_meow : std::bool_constant<meowable<T>> {};
template <typename T>
constexpr bool has_meow_v = has_meow<T>::value;
Application:
std::cout << "Has meow?" << '\n'
<< "Dog: " << has_meow_v<Dog> << '\n'
<< "Cat: " << has_meow_v<Cat> << '\n'
<< "Wolf: " << has_meow_v<Wolf> << '\n';
Which outputs the same as above.
From what I've learned about type traits, they are techniques that give an ability to inspect the "properties" of the type which includes compile-time predicate (not concepts, for example: is_void
, is_bounded_array
). They are part of "reflection" as of now if I'm not mistaken.
My main question is: Would concepts possibly replace type traits?
It seems like a cycle: concepts use type traits, and type traits may possibly use concepts.
- Will concepts help type traits to extend in the world of template metaprogramming?
- When do I apply these concepts or
requires
expressions as a "helper" / "competent" to type traits when "misused" as the same waystd::enable_if
did and maybe not used as a constraint. (It's fine for me if it's misused or applied indirectly to the language)
NOTE: I don't ask how is concepts used in a correct way, but I tried to ask if concepts possibly replace type traits in terms of the compile-time predicate.