首页
学习
活动
专区
圈层
工具
发布
社区首页 >问答首页 >如何遍历std::tuple的元素?

如何遍历std::tuple的元素?
EN

Stack Overflow用户
提问于 2009-07-29 05:57:23
回答 20查看 102.4K关注 0票数 137

我如何迭代一个元组(使用C++11)?我尝试了以下几种方法:

代码语言:javascript
复制
for(int i=0; i<std::tuple_size<T...>::value; ++i) 
  std::get<i>(my_tuple).do_sth();

但这不起作用:

错误1:对不起,未实现:无法展开‘Listener...’转换为固定长度的参数列表。

错误2: I不能出现在常量表达式中。

那么,如何正确地遍历元组的元素呢?

EN

回答 20

Stack Overflow用户

回答已采纳

发布于 2009-07-29 17:41:30

Boost.Fusion是一种可能性:

未经测试的示例:

代码语言:javascript
复制
struct DoSomething
{
    template<typename T>
    void operator()(T& t) const
    {
        t.do_sth();
    }
};

tuple<....> t = ...;
boost::fusion::for_each(t, DoSomething());
票数 28
EN

Stack Overflow用户

发布于 2011-08-01 13:15:34

我有一个基于Iterating over a Tuple的答案

代码语言:javascript
复制
#include <tuple>
#include <utility> 
#include <iostream>

template<std::size_t I = 0, typename... Tp>
inline typename std::enable_if<I == sizeof...(Tp), void>::type
  print(std::tuple<Tp...>& t)
  { }

template<std::size_t I = 0, typename... Tp>
inline typename std::enable_if<I < sizeof...(Tp), void>::type
  print(std::tuple<Tp...>& t)
  {
    std::cout << std::get<I>(t) << std::endl;
    print<I + 1, Tp...>(t);
  }

int
main()
{
  typedef std::tuple<int, float, double> T;
  T t = std::make_tuple(2, 3.14159F, 2345.678);

  print(t);
}

通常的想法是使用编译时递归。事实上,这个想法被用来制作一个类型安全的printf,正如原始元组论文中所指出的那样。

这可以很容易地概括为元组的for_each

代码语言:javascript
复制
#include <tuple>
#include <utility> 

template<std::size_t I = 0, typename FuncT, typename... Tp>
inline typename std::enable_if<I == sizeof...(Tp), void>::type
  for_each(std::tuple<Tp...> &, FuncT) // Unused arguments are given no names.
  { }

template<std::size_t I = 0, typename FuncT, typename... Tp>
inline typename std::enable_if<I < sizeof...(Tp), void>::type
  for_each(std::tuple<Tp...>& t, FuncT f)
  {
    f(std::get<I>(t));
    for_each<I + 1, FuncT, Tp...>(t, f);
  }

尽管这需要一些努力才能让FuncT为元组可能包含的每种类型提供适当的重载。如果您知道所有元组元素都将共享一个公共基类或类似的类,则此方法效果最好。

票数 140
EN

Stack Overflow用户

发布于 2019-01-05 22:43:28

在C++17中,您可以将std::applyfold expression一起使用

代码语言:javascript
复制
std::apply([](auto&&... args) {((/* args.dosomething() */), ...);}, the_tuple);

打印元组的完整示例:

代码语言:javascript
复制
#include <tuple>
#include <iostream>

int main()
{
    std::tuple t{42, 'a', 4.2}; // Another C++17 feature: class template argument deduction
    std::apply([](auto&&... args) {((std::cout << args << '\n'), ...);}, t);
}

[Online Example on Coliru]

该方案解决了M. Alaggan's answer中的求值顺序问题。

票数 100
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/1198260

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档