1 //===----------------------------------------------------------------------===//
2 //
3 //                     The LLVM Compiler Infrastructure
4 //
5 // This file is dual licensed under the MIT and the University of Illinois Open
6 // Source Licenses. See LICENSE.TXT for details.
7 //
8 //===----------------------------------------------------------------------===//
9 
10 // <tuple>
11 
12 // template <class... Types> class tuple;
13 
14 // constexpr tuple();
15 
16 // UNSUPPORTED: c++98, c++03
17 
18 #include <tuple>
19 #include <string>
20 #include <cassert>
21 #include <type_traits>
22 
23 #include "DefaultOnly.h"
24 
25 struct NoDefault {
26     NoDefault() = delete;
NoDefaultNoDefault27     explicit NoDefault(int) { }
28 };
29 
30 struct NoExceptDefault {
31     NoExceptDefault() noexcept = default;
32 };
33 
34 struct ThrowingDefault {
ThrowingDefaultThrowingDefault35     ThrowingDefault() { }
36 };
37 
38 struct IllFormedDefault {
IllFormedDefaultIllFormedDefault39     IllFormedDefault(int x) : value(x) {}
40     template <bool Pred = false>
IllFormedDefaultIllFormedDefault41     constexpr IllFormedDefault() {
42         static_assert(Pred,
43             "The default constructor should not be instantiated");
44     }
45     int value;
46 };
47 
main()48 int main()
49 {
50     {
51         std::tuple<> t;
52     }
53     {
54         std::tuple<int> t;
55         assert(std::get<0>(t) == 0);
56     }
57     {
58         std::tuple<int, char*> t;
59         assert(std::get<0>(t) == 0);
60         assert(std::get<1>(t) == nullptr);
61     }
62     {
63         std::tuple<int, char*, std::string> t;
64         assert(std::get<0>(t) == 0);
65         assert(std::get<1>(t) == nullptr);
66         assert(std::get<2>(t) == "");
67     }
68     {
69         std::tuple<int, char*, std::string, DefaultOnly> t;
70         assert(std::get<0>(t) == 0);
71         assert(std::get<1>(t) == nullptr);
72         assert(std::get<2>(t) == "");
73         assert(std::get<3>(t) == DefaultOnly());
74     }
75     {
76         // See bug #21157.
77         static_assert(!std::is_default_constructible<std::tuple<NoDefault>>(), "");
78         static_assert(!std::is_default_constructible<std::tuple<DefaultOnly, NoDefault>>(), "");
79         static_assert(!std::is_default_constructible<std::tuple<NoDefault, DefaultOnly, NoDefault>>(), "");
80     }
81     {
82         static_assert(noexcept(std::tuple<NoExceptDefault>()), "");
83         static_assert(noexcept(std::tuple<NoExceptDefault, NoExceptDefault>()), "");
84 
85         static_assert(!noexcept(std::tuple<ThrowingDefault, NoExceptDefault>()), "");
86         static_assert(!noexcept(std::tuple<NoExceptDefault, ThrowingDefault>()), "");
87         static_assert(!noexcept(std::tuple<ThrowingDefault, ThrowingDefault>()), "");
88     }
89 #ifndef _LIBCPP_HAS_NO_CONSTEXPR
90     {
91         constexpr std::tuple<> t;
92     }
93     {
94         constexpr std::tuple<int> t;
95         assert(std::get<0>(t) == 0);
96     }
97     {
98         constexpr std::tuple<int, char*> t;
99         assert(std::get<0>(t) == 0);
100         assert(std::get<1>(t) == nullptr);
101     }
102     {
103     // Check that the SFINAE on the default constructor is not evaluted when
104     // it isn't needed. If the default constructor is evaluted then this test
105     // should fail to compile.
106         IllFormedDefault v(0);
107         std::tuple<IllFormedDefault> t(v);
108     }
109 #endif
110 }
111