| 
8 | 8 | 
 
  | 
9 | 9 | // UNSUPPORTED: c++03, c++11  | 
10 | 10 | 
 
  | 
11 |  | -#include <utility>  | 
12 |  | -#include <string>  | 
13 |  | -#include <type_traits>  | 
 | 11 | +#include <cassert>  | 
14 | 12 | #include <complex>  | 
15 | 13 | #include <memory>  | 
16 |  | - | 
17 |  | -#include <cassert>  | 
 | 14 | +#include <type_traits>  | 
 | 15 | +#include <utility>  | 
18 | 16 | 
 
  | 
19 | 17 | #include "test_macros.h"  | 
20 | 18 | 
 
  | 
21 |  | -int main(int, char**)  | 
22 |  | -{  | 
23 |  | -    typedef std::complex<float> cf;  | 
24 |  | -    {  | 
25 |  | -    auto t1 = std::make_pair<int, cf> ( 42, { 1,2 } );  | 
26 |  | -    assert ( std::get<int>(t1) == 42 );  | 
27 |  | -    assert ( std::get<cf>(t1).real() == 1 );  | 
28 |  | -    assert ( std::get<cf>(t1).imag() == 2 );  | 
29 |  | -    }  | 
 | 19 | +TEST_CONSTEXPR_CXX14 bool test() {  | 
 | 20 | +  { // Make sure that references work as expected  | 
 | 21 | +    int i = 1;  | 
 | 22 | +    int j = 2;  | 
30 | 23 | 
 
  | 
31 | 24 |     {  | 
32 |  | -    const std::pair<int, const int> p1 { 1, 2 };  | 
33 |  | -    const int &i1 = std::get<int>(p1);  | 
34 |  | -    const int &i2 = std::get<const int>(p1);  | 
35 |  | -    assert ( i1 == 1 );  | 
36 |  | -    assert ( i2 == 2 );  | 
37 |  | -    }  | 
 | 25 | +      std::pair<int&, int&&> p(i, std::move(j));  | 
 | 26 | +      assert(&std::get<int&>(p) == &i);  | 
 | 27 | +      assert(&std::get<int&&>(p) == &j);  | 
38 | 28 | 
 
  | 
39 |  | -    {  | 
40 |  | -    typedef std::unique_ptr<int> upint;  | 
41 |  | -    std::pair<upint, int> t(upint(new int(4)), 42);  | 
42 |  | -    upint p = std::get<upint>(std::move(t)); // get rvalue  | 
43 |  | -    assert(*p == 4);  | 
44 |  | -    assert(std::get<upint>(t) == nullptr); // has been moved from  | 
 | 29 | +      assert(&std::get<int&>(std::move(p)) == &i);  | 
 | 30 | +      assert(std::get<int&&>(std::move(p)) == 2);  | 
 | 31 | + | 
 | 32 | +      const std::pair<int&, int&&> cp(i, std::move(j));  | 
 | 33 | +      assert(&std::get<int&>(cp) == &i);  | 
 | 34 | +      assert(&std::get<int&&>(cp) == &j);  | 
 | 35 | + | 
 | 36 | +      assert(&std::get<int&>(std::move(cp)) == &i);  | 
 | 37 | +      assert(std::get<int&&>(std::move(cp)) == 2);  | 
45 | 38 |     }  | 
46 | 39 | 
 
  | 
47 | 40 |     {  | 
48 |  | -    typedef std::unique_ptr<int> upint;  | 
49 |  | -    const std::pair<upint, int> t(upint(new int(4)), 42);  | 
50 |  | -    static_assert(std::is_same<const upint&&, decltype(std::get<upint>(std::move(t)))>::value, "");  | 
51 |  | -    static_assert(noexcept(std::get<upint>(std::move(t))), "");  | 
52 |  | -    static_assert(std::is_same<const int&&, decltype(std::get<int>(std::move(t)))>::value, "");  | 
53 |  | -    static_assert(noexcept(std::get<int>(std::move(t))), "");  | 
54 |  | -    auto&& p = std::get<upint>(std::move(t)); // get const rvalue  | 
55 |  | -    auto&& i = std::get<int>(std::move(t)); // get const rvalue  | 
56 |  | -    assert(*p == 4);  | 
57 |  | -    assert(i == 42);  | 
58 |  | -    assert(std::get<upint>(t) != nullptr);  | 
 | 41 | +      std::pair<int&&, int&> p(std::move(i), j);  | 
 | 42 | +      assert(&std::get<int&>(p) == &j);  | 
 | 43 | +      assert(&std::get<int&&>(p) == &i);  | 
 | 44 | + | 
 | 45 | +      assert(&std::get<int&>(std::move(p)) == &j);  | 
 | 46 | +      assert(std::get<int&&>(std::move(p)) == 1);  | 
 | 47 | + | 
 | 48 | +      const std::pair<int&&, int&> cp(std::move(i), j);  | 
 | 49 | +      assert(&std::get<int&>(cp) == &j);  | 
 | 50 | +      assert(&std::get<int&&>(cp) == &i);  | 
 | 51 | + | 
 | 52 | +      assert(&std::get<int&>(std::move(cp)) == &j);  | 
 | 53 | +      assert(std::get<int&&>(std::move(cp)) == 1);  | 
59 | 54 |     }  | 
 | 55 | +  }  | 
60 | 56 | 
 
  | 
61 |  | -    {  | 
62 |  | -    int x = 42;  | 
 | 57 | +  {  | 
 | 58 | +    typedef std::complex<float> cf;  | 
 | 59 | +    auto t1  = std::make_pair<int, cf>(42, {1, 2});  | 
 | 60 | +    assert(std::get<int>(t1) == 42);  | 
 | 61 | +    assert(std::get<cf>(t1).real() == 1);  | 
 | 62 | +    assert(std::get<cf>(t1).imag() == 2);  | 
 | 63 | +  }  | 
 | 64 | + | 
 | 65 | +  {  | 
 | 66 | +    const std::pair<int, const int> p1{1, 2};  | 
 | 67 | +    const int& i1 = std::get<int>(p1);  | 
 | 68 | +    const int& i2 = std::get<const int>(p1);  | 
 | 69 | +    assert(i1 == 1);  | 
 | 70 | +    assert(i2 == 2);  | 
 | 71 | +  }  | 
 | 72 | + | 
 | 73 | +  {  | 
 | 74 | +    int x       = 42;  | 
63 | 75 |     int const y = 43;  | 
64 | 76 |     std::pair<int&, int const&> const p(x, y);  | 
65 | 77 |     static_assert(std::is_same<int&, decltype(std::get<int&>(std::move(p)))>::value, "");  | 
66 | 78 |     static_assert(noexcept(std::get<int&>(std::move(p))), "");  | 
67 | 79 |     static_assert(std::is_same<int const&, decltype(std::get<int const&>(std::move(p)))>::value, "");  | 
68 | 80 |     static_assert(noexcept(std::get<int const&>(std::move(p))), "");  | 
69 |  | -    }  | 
 | 81 | +  }  | 
70 | 82 | 
 
  | 
71 |  | -    {  | 
72 |  | -    int x = 42;  | 
 | 83 | +  {  | 
 | 84 | +    int x       = 42;  | 
73 | 85 |     int const y = 43;  | 
74 | 86 |     std::pair<int&&, int const&&> const p(std::move(x), std::move(y));  | 
75 | 87 |     static_assert(std::is_same<int&&, decltype(std::get<int&&>(std::move(p)))>::value, "");  | 
76 | 88 |     static_assert(noexcept(std::get<int&&>(std::move(p))), "");  | 
77 | 89 |     static_assert(std::is_same<int const&&, decltype(std::get<int const&&>(std::move(p)))>::value, "");  | 
78 | 90 |     static_assert(noexcept(std::get<int const&&>(std::move(p))), "");  | 
79 |  | -    }  | 
 | 91 | +  }  | 
80 | 92 | 
 
  | 
81 |  | -    {  | 
82 |  | -    constexpr const std::pair<int, const int> p { 1, 2 };  | 
 | 93 | +  {  | 
 | 94 | +    constexpr const std::pair<int, const int> p{1, 2};  | 
83 | 95 |     static_assert(std::get<int>(std::move(p)) == 1, "");  | 
84 | 96 |     static_assert(std::get<const int>(std::move(p)) == 2, "");  | 
85 |  | -    }  | 
 | 97 | +  }  | 
 | 98 | + | 
 | 99 | +  return true;  | 
 | 100 | +}  | 
 | 101 | + | 
 | 102 | +int main(int, char**) {  | 
 | 103 | +  test();  | 
 | 104 | +#if TEST_STD_VER >= 14  | 
 | 105 | +  static_assert(test(), "");  | 
 | 106 | +#endif  | 
 | 107 | + | 
 | 108 | +  // These tests use types which only work during constant evaluation in very recent standards  | 
 | 109 | + | 
 | 110 | +  {  | 
 | 111 | +    typedef std::unique_ptr<int> upint;  | 
 | 112 | +    std::pair<upint, int> t(upint(new int(4)), 42);  | 
 | 113 | +    upint p = std::get<upint>(std::move(t)); // get rvalue  | 
 | 114 | +    assert(*p == 4);  | 
 | 115 | +    assert(std::get<upint>(t) == nullptr); // has been moved from  | 
 | 116 | +  }  | 
 | 117 | + | 
 | 118 | +  {  | 
 | 119 | +    typedef std::unique_ptr<int> upint;  | 
 | 120 | +    const std::pair<upint, int> t(upint(new int(4)), 42);  | 
 | 121 | +    static_assert(std::is_same<const upint&&, decltype(std::get<upint>(std::move(t)))>::value, "");  | 
 | 122 | +    static_assert(noexcept(std::get<upint>(std::move(t))), "");  | 
 | 123 | +    static_assert(std::is_same<const int&&, decltype(std::get<int>(std::move(t)))>::value, "");  | 
 | 124 | +    static_assert(noexcept(std::get<int>(std::move(t))), "");  | 
 | 125 | +    auto&& p = std::get<upint>(std::move(t)); // get const rvalue  | 
 | 126 | +    auto&& i = std::get<int>(std::move(t));   // get const rvalue  | 
 | 127 | +    assert(*p == 4);  | 
 | 128 | +    assert(i == 42);  | 
 | 129 | +    assert(std::get<upint>(t) != nullptr);  | 
 | 130 | +  }  | 
86 | 131 | 
 
  | 
87 | 132 |   return 0;  | 
88 | 133 | }  | 
0 commit comments