gpt4 book ai didi

c++ - 将函数应用于元组的每个元素

转载 作者:可可西里 更新时间:2023-11-01 16:39:10 25 4
gpt4 key购买 nike

给定一个类似于 std::tuple 的对象(即具有定义的 tuple_sizeget 语义)和一个一元仿函数对象 ftor,我希望能够在类似 tuple 的对象的每个元素上调用 ftor

如果我忽略返回值,我知道 int 数组技巧:

namespace details {

template <typename Ftor, typename Tuple, size_t... Is>
void apply_unary(Ftor&& ftor, Tuple&& tuple, std::index_sequence<Is...>) {
using std::get;
int arr[] = { (ftor(get<Is>(std::forward<Tuple>(tuple))), void(), 0)... };
}

} // namespace details

template <typename Ftor, typename Tuple>
void apply_unary(Ftor&& ftor, Tuple&& tuple) {
details::apply_unary(std::forward<Ftor>(ftor),
std::forward<Tuple>(tuple),
std::make_index_sequence<std::tuple_size<Tuple>::value> {});
}

如果我想要返回值,我可以将 int [] 技巧替换为调用 std::make_tuple 并将其返回。如果对 ftor 对象的调用都没有 void 返回值...

因此我的问题是:考虑到我想获得调用的结果,我该如何处理可能返回 void 的调用?

唯一的要求是我应该将结果作为元组获取,并且能够分辨出哪个调用导致所述结果元组的哪个元素。

最佳答案

正如@Jarod42 所建议的那样,用一个额外的层包装调用,该层负责用虚拟结构替换 void return 将达到目的:

struct no_return {};

namespace details {

template <typename Ftor, typename Arg>
auto call(Ftor&& ftor, Arg&& arg)
-> std::enable_if_t<std::is_void<decltype(std::forward<Ftor>(ftor)(std::forward<Arg>(arg)))>::value, no_return> {
std::forward<Ftor>(ftor)(std::forward<Arg>(arg));
return no_return {};
}

template <typename Ftor, typename Arg>
auto call(Ftor&& ftor, Arg&& arg)
-> std::enable_if_t<!std::is_void<decltype(std::forward<Ftor>(ftor)(std::forward<Arg>(arg)))>::value, decltype(std::forward<Ftor>(ftor)(std::forward<Arg>(arg)))> {
return std::forward<Ftor>(ftor)(std::forward<Arg>(arg));
}

template <typename Ftor, typename Tuple, size_t... Is>
auto apply_unary(Ftor&& ftor, Tuple&& tuple, std::index_sequence<Is...>) {
using std::get;
return std::tuple<decltype(call(ftor, get<Is>(std::forward<Tuple>(tuple))))...> { call(ftor, get<Is>(std::forward<Tuple>(tuple)))... } ;
}

} // namespace details

template <typename Ftor, typename Tuple>
auto apply_unary(Ftor&& ftor, Tuple&& tuple) {
return details::apply_unary(std::forward<Ftor>(ftor),
std::forward<Tuple>(tuple),
std::make_index_sequence<std::tuple_size<std::decay_t<Tuple> >::value> {});
}

现场演示可在 Coliru 上获得

我使用 SFINAE 来区分这两个重载。它看起来有点丑,所以如果您有任何改进建议...我洗耳恭听!

关于c++ - 将函数应用于元组的每个元素,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/47153933/

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