When you use templates in C++, the user can normally plug any C type in a program. For a template class I developed (read C++ callbacks and templates ), I want to restrict one of the template arguments: R. This is the type of the return value of a callback function. The restriction that I want to impose, is that the function should not return an object, array, string, ... . Numeric and bool types should do. Or return nothing (void).
I want to be able to return a 0 if no function is set in _callback. So as long as the return value is a C++ arithmetic types, I'll be good. My mechanism will fail if a developer wants to use functions that return strings, arrays, objects, ...
I think that being able to return any arithmetic type is flexible enough for a generic callback handler.
template <typename R, typename... Args> // restrict to arithmetic data types for return value, or void requires std::is_void<R>::value || std::is_arithmetic_v<R> class Callback { // ... /* * R can either be an arithmetic type, or void */ inline R call(Args... args) { if constexpr (std::is_void<R>::value) { if (_callback == nullptr) { return; } (*_callback)(args...); } if constexpr (! std::is_void<R>::value) { if (_callback == nullptr) { return 0; // R can only be a arithmetic type. 0 should work as default. } return (*_callback)(args...); } } // ...
I could do nothing. In that case the developer would get a compilation error on this line in my code: return 0;. And they 'll have to go and investigate why my code throws an error.
C++ now has a mechanism that's called concept. With that, I can restrict the C++ type that a particular template attribute can have. I will use that to only allow arithmetic types for the return value type R.
When doing that, the compiler will give a clear message, pointing to the user's code line where they defined an invalid return type:
78 | Callback<std::string, const int&, const int&> cb;
error: template constraint failure for 'template<class R, class ... Args> requires std::is_arithmetic<_Tp>::value class Callback'note: constraints not satisfied
Thank you for reading. Check C++ and templates: callbacks that return a value, or a void for yet another dive into hip C++...