1. 基本介绍

tuple 是 C++11 新标准里的类型,它是一个类似 pair 类型的模板。tuple 是一个固定大小的不同类型值的集合,是泛化的 std::pair。我们也可以把它当做一个通用的结构体来用,不需要创建结构体又获取结构体的特征,在某些情况下可以取代结构体使程序更简洁直观。std::tuple 理论上可以有无数个任意类型的成员变量,而 std::pair 只能是2个成员,因此在需要保存3个及以上的数据时就需要使用 tuple 元组,而且每个确定的 tuple 类型的成员数目是固定的。

「注意」:使用tuple的相关操作需要包含相应头文件:#include<tuple>

一种实现方式:

#include<iostream>
#include<string>
using namespace std;

template <typename ... Tail> class Tuple;
template<> class Tuple<> {};

template <typename Head, typename ... Tail>
class Tuple<Head, Tail ...> : Tuple<Tail ...> 
{
    Head Val;
public:
    Tuple() {}
    Tuple(Head value, Tail ... tail) : Val(value), Tuple<Tail ...>(tail ...) {}
    Head value() { return Val; }
    Tuple<Tail ...> next() { return *this; }
};

int main()
{
    Tuple<char, double, string> tuple('1', 1.5, "Hello World");
    cout << tuple.value() << endl; // 1
    cout << tuple.next().value() << endl; // 1.5
    cout << tuple.next().next().value() << endl; // Hello World

	return 0;
}

2. tuple 所支持的操作

  • make_tuple(v1,v2,v3,v4…vn) :返回一个给定初始值初始化的tuple,类型从初始值推断。
  • t1 == t2 :当两个tuple具有相同数量的成员且成员对应相等时。
  • t1 != t2 :与上一个相反。
  • get(t) :返回t的第i个数据成员。
  • tuple_size::value :给定了tuple中成员的数量。

3. 基本用法

3.1 定义和初始化

//使用tuple默认构造函数,创建一个空的tuple对象
tuple<string, int, double> t1;  

//使用直接(显式)初始化,不能用“=”初始化
tuple<int, vector<int>> t2(3, { 4, 5, 6 });

//可以用make_tuple()函数生成tuple对象,此处自动推断出t3的类型为tuple<int,int,int>
auto t3 = make_tuple(7, 8, 9); 

//tuple的元素类型可以是一个引用
std::tuple<T1&> t4(ref&); 

3.2 访问

  • get标准库模板进行访问其元素内容
  • tuple_size访问其元素个数
  • tuple_element访问其元素类型
#include<iostream>
#include<string>
#include<tuple>   
using namespace std;

int main()
{
    auto t1 = make_tuple(1, 2, 3, 4.4);
    cout << "第1个元素:" << get<0>(t1) << endl;//和数组一样从0开始计
    cout << "第2个元素:" << get<1>(t1) << endl;
    cout << "第3个元素:" << get<2>(t1) << endl;
    cout << "第4个元素:" << get<3>(t1) << endl;

    typedef tuple<int, float, string>TupleType;
    cout << tuple_size<TupleType>::value << endl;
    tuple_element<1, TupleType>::type fl = 1.0;

    return 0;
}

输出结果:

第1个元素:1
第2个元素:2
第3个元素:3
第4个元素:4.4
3

3.3 tuple 比较和 tuple 作为返回值

如果tuple类型进行比较, 则需要保持元素数量相同, 类型可以比较, 如相同类型, 或可以相互转换类型(int&double);

#include <iostream>  
#include <vector>  
#include <string>  
#include <tuple>  
using namespace std;

tuple<string, int> giveName()
{
    string str("Caroline");
    int a(2023);
    tuple<string, int> t = make_tuple(str, a);
    return t;
}

int main()
{
    tuple<int, double, string> t(64, 128.0, "Caroline");
    tuple<string, string, int> t2 = make_tuple("Caroline", "Wendy", 1992);

    //返回元素个数  
    size_t num = tuple_size<decltype(t)>::value;
    cout << "num = " << num << endl;

    //获取第1个值的元素类型  
    tuple_element<1, decltype(t)>::type cnt = get<1>(t);
    cout << "cnt = " << cnt << endl;

    //比较  
    tuple<int, int> t3(24, 48);
    tuple<double, double> t4(28.0, 56.0);
    bool ret = (t3 < t4);
    cout << "ret = " << ret << endl;

    //tuple作为返回值  
    auto t5 = giveName();
    cout << "name: " << get<0>(t5) << " years: " << get<1>(t5) << endl;

    return 0;
}

输出结果:

num = 3
cnt = 128
ret = 1
name: Caroline years: 2023

3.4 还有一种方法也可以获取元组的值,通过 std::tie 解包tuple

int x, y;
string s;
std::tie(x, s, y) = t; 

通过tie解包后,t中三个值会自动赋值给三个变量。

解包时,我们如果只想解某个位置的值时,可以用std::ignore占位符来表示不解某个位置的值。比如我们只想解第三个值时:

std::tie(std::ignore, std::ignore, y) = t;   // 只解第三个值

3.5 通过 tuple_cat 连接多个 tuple

#include <iostream>  
#include <string>  
#include <tuple>  
using namespace std;

int main()
{
    tuple<int, string, float> t1(10, "test", 3.14);
    int n = 7;
    auto t2 = tuple_cat(t1, make_pair("Foo", "bar"), t1, tie(n));
    n = 10;
    // 10 test 3.14 Foo bar 10 test 3.14 10
    cout << get<0>(t2) << " " << get<1>(t2) << " " << get<2>(t2) << " "
        << get<3>(t2) << " " << get<4>(t2) << " " << get<5>(t2) << " "
        << get<6>(t2) << " " << get<7>(t2) << " " << get<8>(t2) << endl;

    return 0;
}
Logo

旨在为数千万中国开发者提供一个无缝且高效的云端环境,以支持学习、使用和贡献开源项目。

更多推荐