gpt4 book ai didi

c++ - 如何使用编译时索引参数迭代参数包的大小

转载 作者:行者123 更新时间:2023-12-05 03:34:57 25 4
gpt4 key购买 nike

我正在尝试编写一个可变参数模板函数,其中包含一个循环,该循环遍历参数包中的每种类型。我正在使用它来构建一个元组,然后我 apply关于确定模板类型的回调函数。

我想我可以使用 sizeof...(Args) 来做到这一点如下:

template <typename ...Args>
void addCallback(void* handle, std::string address, std::function<void(Args...)> callback)
{

return addMessageCallback(std::move(address), [callback](const ci::osc::Message& message) {
std::tuple<Args...> args;
for (size_t i = 0; i < sizeof...(Args); i++)
{
std::get<i>(args) = message.getArg<std::tuple_element_t<i, decltype(args)>(i);
}

std::apply(callback, std::move(args));
});
}

这不会编译,因为 std::get<i>(args)需要 i成为一个编译时间常量。但是,所有信息在编译时都是可用的。有没有办法使这项工作?我考虑过使用折叠表达式,但是

我正在使用 C++17。

最佳答案

您可以定义一个辅助函数来使用index_sequence展开Tuple的元素并通过折叠表达式赋值。

template<class Tuple, class Message, std::size_t... Is>
void assign_tuple(Tuple& tuple, const Message& message, std::index_sequence<Is...>) {
((std::get<Is>(tuple) = message.getArg<std::tuple_element_t<Is, Tuple>(Is)), ...);
};

template <typename ...Args>
auto addCallback(void* handle, std::string address, std::function<void(Args...)> callback) {
return addMessageCallback(std::move(address), [callback](const ci::osc::Message& message) {
std::tuple<Args...> args;
assign_tuple(args, message, std::make_index_sequence<sizeof...(Args)>{});
std::apply(callback, std::move(args));
});
}

在 C++20 中,您只需在函数内定义模板 lambda 即可。

关于c++ - 如何使用编译时索引参数迭代参数包的大小,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/70005580/

25 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com