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 // <optional>
11
12 // template <class U, class... Args>
13 // void optional<T>::emplace(initializer_list<U> il, Args&&... args);
14
15 #include <experimental/optional>
16 #include <type_traits>
17 #include <cassert>
18 #include <vector>
19
20 #if _LIBCPP_STD_VER > 11
21
22 using std::experimental::optional;
23
24 class X
25 {
26 int i_;
27 int j_ = 0;
28 public:
29 static bool dtor_called;
X()30 constexpr X() : i_(0) {}
X(int i)31 constexpr X(int i) : i_(i) {}
X(std::initializer_list<int> il)32 constexpr X(std::initializer_list<int> il) : i_(il.begin()[0]), j_(il.begin()[1]) {}
~X()33 ~X() {dtor_called = true;}
34
operator ==(const X & x,const X & y)35 friend constexpr bool operator==(const X& x, const X& y)
36 {return x.i_ == y.i_ && x.j_ == y.j_;}
37 };
38
39 bool X::dtor_called = false;
40
41 class Y
42 {
43 int i_;
44 int j_ = 0;
45 public:
Y()46 constexpr Y() : i_(0) {}
Y(int i)47 constexpr Y(int i) : i_(i) {}
Y(std::initializer_list<int> il)48 constexpr Y(std::initializer_list<int> il) : i_(il.begin()[0]), j_(il.begin()[1]) {}
49
operator ==(const Y & x,const Y & y)50 friend constexpr bool operator==(const Y& x, const Y& y)
51 {return x.i_ == y.i_ && x.j_ == y.j_;}
52 };
53
54 class Z
55 {
56 int i_;
57 int j_ = 0;
58 public:
59 static bool dtor_called;
Z()60 constexpr Z() : i_(0) {}
Z(int i)61 constexpr Z(int i) : i_(i) {}
Z(std::initializer_list<int> il)62 constexpr Z(std::initializer_list<int> il) : i_(il.begin()[0]), j_(il.begin()[1])
63 {throw 6;}
~Z()64 ~Z() {dtor_called = true;}
65
operator ==(const Z & x,const Z & y)66 friend constexpr bool operator==(const Z& x, const Z& y)
67 {return x.i_ == y.i_ && x.j_ == y.j_;}
68 };
69
70 bool Z::dtor_called = false;
71
72 #endif // _LIBCPP_STD_VER > 11
73
main()74 int main()
75 {
76 #if _LIBCPP_STD_VER > 11
77 {
78 X x;
79 {
80 optional<X> opt(x);
81 assert(X::dtor_called == false);
82 opt.emplace({1, 2});
83 assert(X::dtor_called == true);
84 assert(*opt == X({1, 2}));
85 }
86 }
87 {
88 optional<std::vector<int>> opt;
89 opt.emplace({1, 2, 3}, std::allocator<int>());
90 assert(static_cast<bool>(opt) == true);
91 assert(*opt == std::vector<int>({1, 2, 3}));
92 }
93 {
94 optional<Y> opt;
95 opt.emplace({1, 2});
96 assert(static_cast<bool>(opt) == true);
97 assert(*opt == Y({1, 2}));
98 }
99 {
100 Z z;
101 optional<Z> opt(z);
102 try
103 {
104 assert(static_cast<bool>(opt) == true);
105 assert(Z::dtor_called == false);
106 opt.emplace({1, 2});
107 }
108 catch (int i)
109 {
110 assert(i == 6);
111 assert(static_cast<bool>(opt) == false);
112 assert(Z::dtor_called == true);
113 }
114 }
115 #endif // _LIBCPP_STD_VER > 11
116 }
117