1bc8d3f97eb5c958007f2713238472e0c1c8fe02Howard Hinnant//===----------------------------------------------------------------------===//
2bc8d3f97eb5c958007f2713238472e0c1c8fe02Howard Hinnant//
3f5256e16dfc425c1d466f6308d4026d529ce9e0bHoward Hinnant//                     The LLVM Compiler Infrastructure
4bc8d3f97eb5c958007f2713238472e0c1c8fe02Howard Hinnant//
5b64f8b07c104c6cc986570ac8ee0ed16a9f23976Howard Hinnant// This file is dual licensed under the MIT and the University of Illinois Open
6b64f8b07c104c6cc986570ac8ee0ed16a9f23976Howard Hinnant// Source Licenses. See LICENSE.TXT for details.
7bc8d3f97eb5c958007f2713238472e0c1c8fe02Howard Hinnant//
8bc8d3f97eb5c958007f2713238472e0c1c8fe02Howard Hinnant//===----------------------------------------------------------------------===//
9bc8d3f97eb5c958007f2713238472e0c1c8fe02Howard Hinnant
10bc8d3f97eb5c958007f2713238472e0c1c8fe02Howard Hinnant// <tuple>
11bc8d3f97eb5c958007f2713238472e0c1c8fe02Howard Hinnant
12bc8d3f97eb5c958007f2713238472e0c1c8fe02Howard Hinnant// template <class... Types> class tuple;
13bc8d3f97eb5c958007f2713238472e0c1c8fe02Howard Hinnant
14bc8d3f97eb5c958007f2713238472e0c1c8fe02Howard Hinnant// template <class... UTypes> tuple(const tuple<UTypes...>& u);
15bc8d3f97eb5c958007f2713238472e0c1c8fe02Howard Hinnant
16f063052fe1d3c7a40de69795228a6334f956b9f9Eric Fiselier// UNSUPPORTED: c++98, c++03
17f063052fe1d3c7a40de69795228a6334f956b9f9Eric Fiselier
18bc8d3f97eb5c958007f2713238472e0c1c8fe02Howard Hinnant#include <tuple>
196b913d7c527b6ced23a26f3a0b633cee2fe4aa1aMarshall Clow#include <utility>
20bc8d3f97eb5c958007f2713238472e0c1c8fe02Howard Hinnant#include <string>
21bc8d3f97eb5c958007f2713238472e0c1c8fe02Howard Hinnant#include <cassert>
22bc8d3f97eb5c958007f2713238472e0c1c8fe02Howard Hinnant
23e619862dbf0c4a46db6e3d816bcafcfef6e85977Stephan T. Lavavej#include "test_macros.h"
24e619862dbf0c4a46db6e3d816bcafcfef6e85977Stephan T. Lavavej
2595526d31cb9688f74106a58a9e8b5d1f663fcf5aEric Fiselierstruct Explicit {
2695526d31cb9688f74106a58a9e8b5d1f663fcf5aEric Fiselier  int value;
2795526d31cb9688f74106a58a9e8b5d1f663fcf5aEric Fiselier  explicit Explicit(int x) : value(x) {}
2895526d31cb9688f74106a58a9e8b5d1f663fcf5aEric Fiselier};
2995526d31cb9688f74106a58a9e8b5d1f663fcf5aEric Fiselier
3095526d31cb9688f74106a58a9e8b5d1f663fcf5aEric Fiselierstruct Implicit {
3195526d31cb9688f74106a58a9e8b5d1f663fcf5aEric Fiselier  int value;
3295526d31cb9688f74106a58a9e8b5d1f663fcf5aEric Fiselier  Implicit(int x) : value(x) {}
3395526d31cb9688f74106a58a9e8b5d1f663fcf5aEric Fiselier};
3495526d31cb9688f74106a58a9e8b5d1f663fcf5aEric Fiselier
35bc8d3f97eb5c958007f2713238472e0c1c8fe02Howard Hinnantstruct B
36bc8d3f97eb5c958007f2713238472e0c1c8fe02Howard Hinnant{
37bc8d3f97eb5c958007f2713238472e0c1c8fe02Howard Hinnant    int id_;
38bc8d3f97eb5c958007f2713238472e0c1c8fe02Howard Hinnant
39bc8d3f97eb5c958007f2713238472e0c1c8fe02Howard Hinnant    explicit B(int i) : id_(i) {}
40bc8d3f97eb5c958007f2713238472e0c1c8fe02Howard Hinnant};
41bc8d3f97eb5c958007f2713238472e0c1c8fe02Howard Hinnant
42bc8d3f97eb5c958007f2713238472e0c1c8fe02Howard Hinnantstruct D
43bc8d3f97eb5c958007f2713238472e0c1c8fe02Howard Hinnant    : B
44bc8d3f97eb5c958007f2713238472e0c1c8fe02Howard Hinnant{
45bc8d3f97eb5c958007f2713238472e0c1c8fe02Howard Hinnant    explicit D(int i) : B(i) {}
46bc8d3f97eb5c958007f2713238472e0c1c8fe02Howard Hinnant};
47bc8d3f97eb5c958007f2713238472e0c1c8fe02Howard Hinnant
48e619862dbf0c4a46db6e3d816bcafcfef6e85977Stephan T. Lavavej#if TEST_STD_VER > 11
49da0a0e8a1be285d18870955cffc1b51982675dd8Marshall Clow
50da0a0e8a1be285d18870955cffc1b51982675dd8Marshall Clowstruct A
51da0a0e8a1be285d18870955cffc1b51982675dd8Marshall Clow{
52da0a0e8a1be285d18870955cffc1b51982675dd8Marshall Clow    int id_;
53da0a0e8a1be285d18870955cffc1b51982675dd8Marshall Clow
54da0a0e8a1be285d18870955cffc1b51982675dd8Marshall Clow    constexpr A(int i) : id_(i) {}
55da0a0e8a1be285d18870955cffc1b51982675dd8Marshall Clow    friend constexpr bool operator==(const A& x, const A& y) {return x.id_ == y.id_;}
56da0a0e8a1be285d18870955cffc1b51982675dd8Marshall Clow};
57da0a0e8a1be285d18870955cffc1b51982675dd8Marshall Clow
58da0a0e8a1be285d18870955cffc1b51982675dd8Marshall Clowstruct C
59da0a0e8a1be285d18870955cffc1b51982675dd8Marshall Clow{
60da0a0e8a1be285d18870955cffc1b51982675dd8Marshall Clow    int id_;
61da0a0e8a1be285d18870955cffc1b51982675dd8Marshall Clow
62da0a0e8a1be285d18870955cffc1b51982675dd8Marshall Clow    constexpr explicit C(int i) : id_(i) {}
63da0a0e8a1be285d18870955cffc1b51982675dd8Marshall Clow    friend constexpr bool operator==(const C& x, const C& y) {return x.id_ == y.id_;}
64da0a0e8a1be285d18870955cffc1b51982675dd8Marshall Clow};
65da0a0e8a1be285d18870955cffc1b51982675dd8Marshall Clow
66da0a0e8a1be285d18870955cffc1b51982675dd8Marshall Clow#endif
67da0a0e8a1be285d18870955cffc1b51982675dd8Marshall Clow
68bc8d3f97eb5c958007f2713238472e0c1c8fe02Howard Hinnantint main()
69bc8d3f97eb5c958007f2713238472e0c1c8fe02Howard Hinnant{
70bc8d3f97eb5c958007f2713238472e0c1c8fe02Howard Hinnant    {
710e8cbce107862187f8f75c1e8b7e49d11015d9f0Stephan T. Lavavej        typedef std::tuple<long> T0;
720e8cbce107862187f8f75c1e8b7e49d11015d9f0Stephan T. Lavavej        typedef std::tuple<long long> T1;
730e8cbce107862187f8f75c1e8b7e49d11015d9f0Stephan T. Lavavej        T0 t0(2);
74bc8d3f97eb5c958007f2713238472e0c1c8fe02Howard Hinnant        T1 t1 = t0;
75bc8d3f97eb5c958007f2713238472e0c1c8fe02Howard Hinnant        assert(std::get<0>(t1) == 2);
76bc8d3f97eb5c958007f2713238472e0c1c8fe02Howard Hinnant    }
77e619862dbf0c4a46db6e3d816bcafcfef6e85977Stephan T. Lavavej#if TEST_STD_VER > 11
78da0a0e8a1be285d18870955cffc1b51982675dd8Marshall Clow    {
790e8cbce107862187f8f75c1e8b7e49d11015d9f0Stephan T. Lavavej        typedef std::tuple<int> T0;
80da0a0e8a1be285d18870955cffc1b51982675dd8Marshall Clow        typedef std::tuple<A> T1;
810e8cbce107862187f8f75c1e8b7e49d11015d9f0Stephan T. Lavavej        constexpr T0 t0(2);
82da0a0e8a1be285d18870955cffc1b51982675dd8Marshall Clow        constexpr T1 t1 = t0;
83da0a0e8a1be285d18870955cffc1b51982675dd8Marshall Clow        static_assert(std::get<0>(t1) == 2, "");
84da0a0e8a1be285d18870955cffc1b51982675dd8Marshall Clow    }
85da0a0e8a1be285d18870955cffc1b51982675dd8Marshall Clow    {
86da0a0e8a1be285d18870955cffc1b51982675dd8Marshall Clow        typedef std::tuple<int> T0;
87da0a0e8a1be285d18870955cffc1b51982675dd8Marshall Clow        typedef std::tuple<C> T1;
88da0a0e8a1be285d18870955cffc1b51982675dd8Marshall Clow        constexpr T0 t0(2);
89da0a0e8a1be285d18870955cffc1b51982675dd8Marshall Clow        constexpr T1 t1{t0};
90da0a0e8a1be285d18870955cffc1b51982675dd8Marshall Clow        static_assert(std::get<0>(t1) == C(2), "");
91da0a0e8a1be285d18870955cffc1b51982675dd8Marshall Clow    }
92da0a0e8a1be285d18870955cffc1b51982675dd8Marshall Clow#endif
93bc8d3f97eb5c958007f2713238472e0c1c8fe02Howard Hinnant    {
940e8cbce107862187f8f75c1e8b7e49d11015d9f0Stephan T. Lavavej        typedef std::tuple<long, char> T0;
950e8cbce107862187f8f75c1e8b7e49d11015d9f0Stephan T. Lavavej        typedef std::tuple<long long, int> T1;
960e8cbce107862187f8f75c1e8b7e49d11015d9f0Stephan T. Lavavej        T0 t0(2, 'a');
97bc8d3f97eb5c958007f2713238472e0c1c8fe02Howard Hinnant        T1 t1 = t0;
98bc8d3f97eb5c958007f2713238472e0c1c8fe02Howard Hinnant        assert(std::get<0>(t1) == 2);
99bc8d3f97eb5c958007f2713238472e0c1c8fe02Howard Hinnant        assert(std::get<1>(t1) == int('a'));
100bc8d3f97eb5c958007f2713238472e0c1c8fe02Howard Hinnant    }
101bc8d3f97eb5c958007f2713238472e0c1c8fe02Howard Hinnant    {
1020e8cbce107862187f8f75c1e8b7e49d11015d9f0Stephan T. Lavavej        typedef std::tuple<long, char, D> T0;
1030e8cbce107862187f8f75c1e8b7e49d11015d9f0Stephan T. Lavavej        typedef std::tuple<long long, int, B> T1;
1040e8cbce107862187f8f75c1e8b7e49d11015d9f0Stephan T. Lavavej        T0 t0(2, 'a', D(3));
105bc8d3f97eb5c958007f2713238472e0c1c8fe02Howard Hinnant        T1 t1 = t0;
106bc8d3f97eb5c958007f2713238472e0c1c8fe02Howard Hinnant        assert(std::get<0>(t1) == 2);
107bc8d3f97eb5c958007f2713238472e0c1c8fe02Howard Hinnant        assert(std::get<1>(t1) == int('a'));
108bc8d3f97eb5c958007f2713238472e0c1c8fe02Howard Hinnant        assert(std::get<2>(t1).id_ == 3);
109bc8d3f97eb5c958007f2713238472e0c1c8fe02Howard Hinnant    }
110bc8d3f97eb5c958007f2713238472e0c1c8fe02Howard Hinnant    {
111bc8d3f97eb5c958007f2713238472e0c1c8fe02Howard Hinnant        D d(3);
1120e8cbce107862187f8f75c1e8b7e49d11015d9f0Stephan T. Lavavej        typedef std::tuple<long, char, D&> T0;
1130e8cbce107862187f8f75c1e8b7e49d11015d9f0Stephan T. Lavavej        typedef std::tuple<long long, int, B&> T1;
1140e8cbce107862187f8f75c1e8b7e49d11015d9f0Stephan T. Lavavej        T0 t0(2, 'a', d);
115bc8d3f97eb5c958007f2713238472e0c1c8fe02Howard Hinnant        T1 t1 = t0;
116bc8d3f97eb5c958007f2713238472e0c1c8fe02Howard Hinnant        d.id_ = 2;
117bc8d3f97eb5c958007f2713238472e0c1c8fe02Howard Hinnant        assert(std::get<0>(t1) == 2);
118bc8d3f97eb5c958007f2713238472e0c1c8fe02Howard Hinnant        assert(std::get<1>(t1) == int('a'));
119bc8d3f97eb5c958007f2713238472e0c1c8fe02Howard Hinnant        assert(std::get<2>(t1).id_ == 2);
120bc8d3f97eb5c958007f2713238472e0c1c8fe02Howard Hinnant    }
121993248935c459c308379e14ccb09fa1c840d4a9cHoward Hinnant    {
1220e8cbce107862187f8f75c1e8b7e49d11015d9f0Stephan T. Lavavej        typedef std::tuple<long, char, int> T0;
1230e8cbce107862187f8f75c1e8b7e49d11015d9f0Stephan T. Lavavej        typedef std::tuple<long long, int, B> T1;
1240e8cbce107862187f8f75c1e8b7e49d11015d9f0Stephan T. Lavavej        T0 t0(2, 'a', 3);
125993248935c459c308379e14ccb09fa1c840d4a9cHoward Hinnant        T1 t1(t0);
126993248935c459c308379e14ccb09fa1c840d4a9cHoward Hinnant        assert(std::get<0>(t1) == 2);
127993248935c459c308379e14ccb09fa1c840d4a9cHoward Hinnant        assert(std::get<1>(t1) == int('a'));
128993248935c459c308379e14ccb09fa1c840d4a9cHoward Hinnant        assert(std::get<2>(t1).id_ == 3);
129993248935c459c308379e14ccb09fa1c840d4a9cHoward Hinnant    }
13095526d31cb9688f74106a58a9e8b5d1f663fcf5aEric Fiselier    {
13195526d31cb9688f74106a58a9e8b5d1f663fcf5aEric Fiselier        const std::tuple<int> t1(42);
13295526d31cb9688f74106a58a9e8b5d1f663fcf5aEric Fiselier        std::tuple<Explicit> t2(t1);
13395526d31cb9688f74106a58a9e8b5d1f663fcf5aEric Fiselier        assert(std::get<0>(t2).value == 42);
13495526d31cb9688f74106a58a9e8b5d1f663fcf5aEric Fiselier    }
13595526d31cb9688f74106a58a9e8b5d1f663fcf5aEric Fiselier    {
13695526d31cb9688f74106a58a9e8b5d1f663fcf5aEric Fiselier        const std::tuple<int> t1(42);
13795526d31cb9688f74106a58a9e8b5d1f663fcf5aEric Fiselier        std::tuple<Implicit> t2 = t1;
13895526d31cb9688f74106a58a9e8b5d1f663fcf5aEric Fiselier        assert(std::get<0>(t2).value == 42);
13995526d31cb9688f74106a58a9e8b5d1f663fcf5aEric Fiselier    }
140bc8d3f97eb5c958007f2713238472e0c1c8fe02Howard Hinnant}
141