[英]Deduce member function arguments / return type
I have the following code: 我有以下代码:
template <class... Args>
struct TypeList
{
static constexpr size_t size = sizeof...(Args);
template <std::size_t N>
using type = typename std::tuple_element<N, std::tuple<Args...>>::type;
};
struct Generator
{
std::tuple<float, float> process(float, int, size_t)
{
return std::make_tuple(0.0f, 1.0f);
}
};
Is there any way to deduce both the tuple template arguments as well as the input arguments for Generator::process
in order to construct a class that has the following template arguments. 是否有任何方法可以推导出
Generator::process
的元组模板参数和输入参数,以构造具有以下模板参数的类。
struct Node<GenType, ReturnTypesList, ArgumentTypeList>
Where ReturnTypesList
contains template arguments of the returned tuple and ArgumentTypeList
contains the variadic argument types of the process function. 其中
ReturnTypesList
包含返回的元组的模板参数,而ArgumentTypeList
包含流程函数的可变参数类型。 It is assumed that all process functions will return a tuple. 假定所有过程函数都将返回一个元组。
I didn't get exactly what you are looking for, but probably something like this would work for you: 我没有完全找到您想要的东西,但是可能这样的事情对您有用:
#include <type_traits>
#include <tuple>
template <class... Args>
struct TypeList
{
static constexpr size_t size = sizeof...(Args);
template <std::size_t N>
using type = typename std::tuple_element<N, std::tuple<Args...>>::type;
};
struct Generator
{
std::tuple<float, float> process(float, int, size_t)
{
return std::make_tuple(0.0f, 1.0f);
}
};
template<typename GenType, typename ReturnTypesList, typename ArgumentTypeList>
struct Node {};
template<typename T>
struct S
{
template<typename... RArgs, typename... Args>
static auto gen(std::tuple<RArgs...>(T::*)(Args...)) -> Node<T, TypeList<RArgs...>, TypeList<Args...>>;
};
template<typename T>
using NodeType = decltype(S<T>::gen(&T::process));
int main()
{
static_assert(std::is_same<NodeType<Generator>, Node<Generator, TypeList<float, float>, TypeList<float, int, size_t>>>::value, "!");
}
NodeType
is the required type once specialized with the specific generator, as you can see from the test in the main
. NodeType
是曾经专门与特定的发电机,你可以从测试看到所需的类型main
。
In the specific case: 在特定情况下:
Node<Generator, TypeList<float, float>, TypeList<float, int, size_t>>
Don't mind if the member is provided as a function parameter instead of a template argument. 不必介意该成员是否作为函数参数而不是模板参数提供。 The whole thing is solved at compile-time anyway.
整个问题还是在编译时解决了。
As a side note, the solution won't work for those generators that have overloaded process
. 附带说明一下,该解决方案不适用于那些
process
过载的发电机。
#include <tuple>
template <class...>
struct Node;
struct Generator {
std::tuple<float, float> process(float, int, size_t);
};
template <class... Args1, class ClassType, class... Args2>
auto foo(std::tuple<Args1...> (ClassType::*)(Args2...)) -> Node<ClassType, Args1..., Args2...>;
int main() {
// T is Node<Generator, float, float, float, int, size_t>
using T = decltype(foo(&Generator::process));
return 0;
}
Args1
and Args2
are deduced properly because the pack expansion that appears at the very end of the template parameter list will be deduced. 可以正确推导
Args1
和Args2
,因为Args2
导出现在模板参数列表末尾的装箱扩展。 And the member function pointer which is passed to foo
contains all the types necessary. 传递给
foo
的成员函数指针包含所有必需的类型。 All the template parameters of foo
will be deduced separately and then combined to a type which match the type of &Generator::process
after certain adjustment. foo
所有模板参数将分别推导,然后在经过一定的调整后组合为&Generator::process
类型匹配的类型。 Link 链接
Unrelated: If process isn't garanted to return a std::tuple
, we can still use a template template parameter, aka template <class...> class TT
不相关:如果进程不被授权返回
std::tuple
,我们仍然可以使用模板模板参数,也称为template <class...> class TT
template <class...>
struct Node {};
template <class...>
struct TypeList {};
struct Generator {
std::tuple<float, float> process(float, int, size_t) {}
};
template <class... ReturnArgs, class GeneratorType, class... Args>
auto magic(std::tuple<ReturnArgs...> (GeneratorType::*arg)(Args...))
-> Node<GeneratorType, TypeList<ReturnArgs...>, TypeList<Args...> > {
using ReturnType =
Node<GeneratorType, TypeList<ReturnArgs...>, TypeList<Args...> >;
return ReturnType{};
}
int main() {
magic(&Generator::process);
return 0;
}
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.