动态创建和扩展 std::tuple 到参数包
Dynamically creating and expanding std::tuple into parameter pack
我正在为用 C++ 编写的软件编写插件,这里是定义插件的片段:
extern "C"
irods::ms_table_entry* plugin_factory() {
// The number of msParam_t* arguments that it will accept
int numArguments = 2;
irods::ms_table_entry* msvc = new irods::ms_table_entry(numArguments);
msvc->add_operation(
"my_microservice",
std::function<int(msParam_t*, msParam_t*, ruleExecInfo_t*)>(MyMicroservice)
);
return msvc;
}
我希望能够使用 numArguments
动态生成 std::function<int(msParam_t*, msParam_t*, ruleExecInfo_t*)>
参数包。其中 numArguments
表示 msParam_t*
个参数的数量。
我不是 C++ 专家(尤其是模板方面),所以 after some research 我发现 可能 可以通过实施以下内容实现:
- std::tuple
- std::tuple_cat
- std::index_sequence
- std::make_integer_sequence
但我真的不知道如何开始实施它。我找到的例子很难理解,我无法将它们转化为我自己的需求。任何人都可以提供有关这可能如何工作的提示、简短示例或参考吗?非常感谢任何信息!
template<typename T>
struct toFunc;
template<typename...T>
struct toFunc<std::tuple<T...>>
{
using type = std::function<void(T...)>;
};
int main(int argc, char **argv) {
using t = std::tuple<int, int, int>;
using func = toFunc<t>::type;
auto f = func([](int a, int b, int c){std::cout << a << b << c << std::endl;});
f(1, 2, 3);
return 0;
}
toFunc typetrait 会将您的元组转换为函数类型。不确定你是否想要那个。如果你想用你可能需要寻找的参数调用
http://en.cppreference.com/w/cpp/utility/apply
或者您可以使用此实现:
namespace detail
{
template <unsigned int N>
struct for_each_t_idx
{
template <template<std::size_t> class Functor, typename... ArgsT>
static void exec(const std::tuple<ArgsT...>& t, Functor<N> func)
{
for_each_t_idx<N - 1>::exec(t, func);
func<N - 1>(t);
}
};
template <>
struct for_each_t_idx<0>
{
template <template<std::size_t> class Functor, typename... ArgsT>
static void exec(const std::tuple<ArgsT...>& t, Functor<0> func)
{
}
};
}
template <template<std::size_t> class Functor, typename... ArgsT>
void for_each_idx(const std::tuple<ArgsT...>& t, Functor<sizeof...(ArgsT)> func)
{
detail::for_each_t_idx<sizeof...(ArgsT)>::exec(t, func);
}
这将为元组中的每个元素调用给定函数。
我不知道以下内容是否正是您要问的,但我认为您想要的是能够根据参数的数量为 std::function
生成正确的模板参数您的 MyMicroservice
将其存储到 numParameters
变量中。
如果是这种情况,您可以完全省略编写它们并使用 decltype
让编译器为您编写它们。
int myMicroservice1(int a,int b, int c){
return a+b+c;
}
int myMicroservice2(int a,int b, int c,int d){
return a*b*c-d;
}
int myMicroservice3(int a,int b, int c,int d,int e, int f){
return a*b*c+e+f;
}
template<typename... types_t>
void add_operation(const std::string & _op, std::function< int(types_t...)> _f ){
}
int main() {
add_operation("blabla",std::function<decltype(myMicroservice1)>(myMicroservice1));
add_operation("blabla",std::function<decltype(myMicroservice2)>(myMicroservice2));
add_operation("blabla",std::function<decltype(myMicroservice3)>(myMicroservice3));
return 0;
}
我正在为用 C++ 编写的软件编写插件,这里是定义插件的片段:
extern "C"
irods::ms_table_entry* plugin_factory() {
// The number of msParam_t* arguments that it will accept
int numArguments = 2;
irods::ms_table_entry* msvc = new irods::ms_table_entry(numArguments);
msvc->add_operation(
"my_microservice",
std::function<int(msParam_t*, msParam_t*, ruleExecInfo_t*)>(MyMicroservice)
);
return msvc;
}
我希望能够使用 numArguments
动态生成 std::function<int(msParam_t*, msParam_t*, ruleExecInfo_t*)>
参数包。其中 numArguments
表示 msParam_t*
个参数的数量。
我不是 C++ 专家(尤其是模板方面),所以 after some research 我发现 可能 可以通过实施以下内容实现:
- std::tuple
- std::tuple_cat
- std::index_sequence
- std::make_integer_sequence
但我真的不知道如何开始实施它。我找到的例子很难理解,我无法将它们转化为我自己的需求。任何人都可以提供有关这可能如何工作的提示、简短示例或参考吗?非常感谢任何信息!
template<typename T>
struct toFunc;
template<typename...T>
struct toFunc<std::tuple<T...>>
{
using type = std::function<void(T...)>;
};
int main(int argc, char **argv) {
using t = std::tuple<int, int, int>;
using func = toFunc<t>::type;
auto f = func([](int a, int b, int c){std::cout << a << b << c << std::endl;});
f(1, 2, 3);
return 0;
}
toFunc typetrait 会将您的元组转换为函数类型。不确定你是否想要那个。如果你想用你可能需要寻找的参数调用 http://en.cppreference.com/w/cpp/utility/apply
或者您可以使用此实现:
namespace detail
{
template <unsigned int N>
struct for_each_t_idx
{
template <template<std::size_t> class Functor, typename... ArgsT>
static void exec(const std::tuple<ArgsT...>& t, Functor<N> func)
{
for_each_t_idx<N - 1>::exec(t, func);
func<N - 1>(t);
}
};
template <>
struct for_each_t_idx<0>
{
template <template<std::size_t> class Functor, typename... ArgsT>
static void exec(const std::tuple<ArgsT...>& t, Functor<0> func)
{
}
};
}
template <template<std::size_t> class Functor, typename... ArgsT>
void for_each_idx(const std::tuple<ArgsT...>& t, Functor<sizeof...(ArgsT)> func)
{
detail::for_each_t_idx<sizeof...(ArgsT)>::exec(t, func);
}
这将为元组中的每个元素调用给定函数。
我不知道以下内容是否正是您要问的,但我认为您想要的是能够根据参数的数量为 std::function
生成正确的模板参数您的 MyMicroservice
将其存储到 numParameters
变量中。
如果是这种情况,您可以完全省略编写它们并使用 decltype
让编译器为您编写它们。
int myMicroservice1(int a,int b, int c){
return a+b+c;
}
int myMicroservice2(int a,int b, int c,int d){
return a*b*c-d;
}
int myMicroservice3(int a,int b, int c,int d,int e, int f){
return a*b*c+e+f;
}
template<typename... types_t>
void add_operation(const std::string & _op, std::function< int(types_t...)> _f ){
}
int main() {
add_operation("blabla",std::function<decltype(myMicroservice1)>(myMicroservice1));
add_operation("blabla",std::function<decltype(myMicroservice2)>(myMicroservice2));
add_operation("blabla",std::function<decltype(myMicroservice3)>(myMicroservice3));
return 0;
}