C ++ template template custom parameter

I am trying to achieve the following:

template<template<typename> bool Function_, typename ... Types_> constexpr auto find(Tuple<Types_ ... >) noexcept { // ... } 

where a possible function could be:

 template<typename T> inline constexpr bool is_pointer_v = is_pointer<T>::value; 

then using find will be:

 Tuple<int, char, void *> t; find<is_pointer_v>(t); 

don't worry about the implementation of find, I'm just asking how to make " template < typename > bool Function_ ", since the bool part is currently not valid in C ++.

any help is appreciated!

EDIT:

here is an example of why I cannot pass " is_pointer " to a function:

 template<typename T_> constexpr auto add_pointer(Type<T_>) noexcept { return type_c<T_ *>; } template<typename F_, typename T_> constexpr auto apply(F_ f, Type<T_> t) noexcept { return f(t); } int main(void) { Type<int> t_i; apply(add_pointer, t_i); } 

a compiler error occurs:

error: there is no corresponding function to call "apply" (<unresolved overloaded function type>, sigma :: meta :: Type &) apply (add_pointer, t_i);

+5
source share
2 answers

any help is appreciated!

You can simply wrap your functions in functors.
As a minimal working example:

 template<typename> struct Type {}; template<typename> struct type_c {}; template<typename T_> struct add_pointer { static constexpr auto invoke(Type<T_>) noexcept { return type_c<T_ *>{}; } }; template<template<typename> class F_, typename T_> constexpr auto apply(Type<T_> t) noexcept { return F_<T_>::invoke(t); } int main(void) { Type<int> t_i; apply<add_pointer>(t_i); } 

If you cannot directly change them, create functors that send everything to the desired function through the static constexpr method.

+2
source

I am just asking how to make "template & lten typename> bool Function_", since the bool part is not valid in C ++ at the moment.

As far as I know, template template arguments are a completely different matter. They are intended for containers, not functions. So class , not bool .

here is an example of why I cannot pass "is_pointer" to a function

Your example does not work because add_pointer is a template function, so when you call

 apply(add_pointer, t_i); 

the compiler does not know which version (type T ) add_pointer use.

The solution may be explicit, as in the following simplified example.

 #include <tuple> #include <iostream> template <typename T> constexpr auto add_pointer(std::tuple<T>) noexcept { std::cout << "add_pointer" << std::endl; return 0; } template <typename F, typename T> constexpr auto apply(F f, std::tuple<T> t) noexcept { return f(t); } int main(void) { std::tuple<int> t_i { 1 }; apply<int(*)(std::tuple<int>)>(add_pointer, t_i); } 

but I understand that explaining int(*)(std::tuple<int>) is a big pain in the ass.

You can simplify the use of the fact that you pass T so that you can deduce the type of the argument received by the function, but (for a general solution) I don’t know how to avoid explicitly returning the type of the function (maybe this is possible, but (at this point) I do not know.

This way you can simplify the call as follows

 apply<int>(add_pointer, t_i); 

and below is a more general example

 #include <tuple> #include <iostream> template <typename ... Ts> constexpr auto add_pointer(std::tuple<Ts...> const &) noexcept { std::cout << "add_pointer" << std::endl; return 0; } template <typename R, typename ... Ts, typename F = R(*)(std::tuple<Ts...> const &)> constexpr auto apply(F f, std::tuple<Ts...> t) noexcept { return f(t); } int main(void) { std::tuple<int> t_i { 1 }; apply<int>(add_pointer, t_i); } 
+1
source

Source: https://habr.com/ru/post/1269742/


All Articles