给定任何函数(或可调用)类型
,我如何获取其所有参数类型作为元组类型?Function
例如,我需要一个特质
function_traits<Function>::arguments
,其中:
int f();
typename function_traits<decltype(f)>::arguments // => gives me std::tuple<>
void g(int);
typename function_traits<decltype(g)>::arguments // => gives me std::tuple<int>
void h(int, int);
typename function_traits<decltype(h)>::arguments // => gives me std::tuple<int, int>
我需要获取参数的大小,幸运的是boost已经实现了
function_traits<F>::arity
从1生成一个
std::integer_sequence
到artify,将其映射到arguments类型,但是问题来了,要映射integer_sequence
,我需要这样的东西:
function_traits<F>::arg_type<N> // -> N-th arg_type
但是 boost 只能提供这个:
function_traits<F>::argN_type
我该如何实施
function_traits<F>::arg_type<N>
?我可以使用 C++ 标准直至 c++17
类似这样的:
#include <tuple>
template<typename x_Function> class
function_traits;
// specialization for functions
template<typename x_Result, typename... x_Args> class
function_traits<x_Result (x_Args...)>
{
public: using arguments = ::std::tuple<x_Args...>;
};
使用示例:
#include <type_traits>
int foo(int);
using foo_arguments = function_traits<decltype(foo)>::arguments;
static_assert(1 == ::std::tuple_size<foo_arguments>::value);
static_assert(::std::is_same_v<int, ::std::tuple_element<0, foo_arguments>::type>);
玩太晚了吗?
你可以使用C++17所以...使用
std::function
演绎指南怎么样?
template <typename T>
struct function_traits
{
template <typename R, typename ... As>
static std::tuple<As...> pro_args (std::function<R(As...)>);
using arguments = decltype(pro_args(std::function{std::declval<T>()}));
};
以下是完整的编译示例
#include <tuple>
#include <functional>
#include <type_traits>
int f ();
void g (int);
void h (int, int);
template <typename T>
struct function_traits
{
template <typename R, typename ... As>
static std::tuple<As...> pro_args (std::function<R(As...)>);
using arguments = decltype(pro_args(std::function{std::declval<T>()}));
};
int main ()
{
static_assert(std::is_same_v<std::tuple<>,
function_traits<decltype(f)>::arguments>);
static_assert(std::is_same_v<std::tuple<int>,
function_traits<decltype(g)>::arguments>);
static_assert(std::is_same_v<std::tuple<int, int>,
function_traits<decltype(h)>::arguments>);
}
现在已经是几年后的事了,但如果您仍然需要它(如果您没有锁定在 Boost 中),我有一个非常有效(免费)的解决方案。由于对我找到的处理函数特征的解决方案(包括 Boost 的解决方案)不满意(既不是“function_traits”也不是“callable_traits”),我编写了自己的解决方案,并将其发布在 GitHub 上供 C++ 开发人员社区使用。我相信它是您目前能找到的同类库中最完整的(专业编写和完整记录)。
参见 https://stackoverflow.com/a/76253527/698767(以及那里引用的链接)。
请注意,那里的示例也解决了您的问题。