]> CyberLeo.Net >> Repos - FreeBSD/FreeBSD.git/blob - contrib/libc++/include/optional
Upgrade our copies of clang, llvm, lld, lldb, compiler-rt and libc++ to
[FreeBSD/FreeBSD.git] / contrib / libc++ / include / optional
1 // -*- C++ -*-
2 //===-------------------------- optional ----------------------------------===//
3 //
4 //                     The LLVM Compiler Infrastructure
5 //
6 // This file is dual licensed under the MIT and the University of Illinois Open
7 // Source Licenses. See LICENSE.TXT for details.
8 //
9 //===----------------------------------------------------------------------===//
10
11 #ifndef _LIBCPP_OPTIONAL
12 #define _LIBCPP_OPTIONAL
13
14 /*
15     optional synopsis
16
17 // C++1z
18
19 namespace std {
20   // 23.6.3, optional for object types
21   template <class T> class optional;
22
23   // 23.6.4, no-value state indicator
24   struct nullopt_t{see below };
25   inline constexpr nullopt_t nullopt(unspecified );
26
27   // 23.6.5, class bad_optional_access
28   class bad_optional_access;
29
30   // 23.6.6, relational operators
31   template <class T, class U>
32   constexpr bool operator==(const optional<T>&, const optional<U>&);
33   template <class T, class U>
34   constexpr bool operator!=(const optional<T>&, const optional<U>&);
35   template <class T, class U>
36   constexpr bool operator<(const optional<T>&, const optional<U>&);
37   template <class T, class U>
38   constexpr bool operator>(const optional<T>&, const optional<U>&);
39   template <class T, class U>
40   constexpr bool operator<=(const optional<T>&, const optional<U>&);
41   template <class T, class U>
42   constexpr bool operator>=(const optional<T>&, const optional<U>&);
43
44   // 23.6.7 comparison with nullopt
45   template <class T> constexpr bool operator==(const optional<T>&, nullopt_t) noexcept;
46   template <class T> constexpr bool operator==(nullopt_t, const optional<T>&) noexcept;
47   template <class T> constexpr bool operator!=(const optional<T>&, nullopt_t) noexcept;
48   template <class T> constexpr bool operator!=(nullopt_t, const optional<T>&) noexcept;
49   template <class T> constexpr bool operator<(const optional<T>&, nullopt_t) noexcept;
50   template <class T> constexpr bool operator<(nullopt_t, const optional<T>&) noexcept;
51   template <class T> constexpr bool operator<=(const optional<T>&, nullopt_t) noexcept;
52   template <class T> constexpr bool operator<=(nullopt_t, const optional<T>&) noexcept;
53   template <class T> constexpr bool operator>(const optional<T>&, nullopt_t) noexcept;
54   template <class T> constexpr bool operator>(nullopt_t, const optional<T>&) noexcept;
55   template <class T> constexpr bool operator>=(const optional<T>&, nullopt_t) noexcept;
56   template <class T> constexpr bool operator>=(nullopt_t, const optional<T>&) noexcept;
57
58   // 23.6.8, comparison with T
59   template <class T, class U> constexpr bool operator==(const optional<T>&, const U&);
60   template <class T, class U> constexpr bool operator==(const T&, const optional<U>&);
61   template <class T, class U> constexpr bool operator!=(const optional<T>&, const U&);
62   template <class T, class U> constexpr bool operator!=(const T&, const optional<U>&);
63   template <class T, class U> constexpr bool operator<(const optional<T>&, const U&);
64   template <class T, class U> constexpr bool operator<(const T&, const optional<U>&);
65   template <class T, class U> constexpr bool operator<=(const optional<T>&, const U&);
66   template <class T, class U> constexpr bool operator<=(const T&, const optional<U>&);
67   template <class T, class U> constexpr bool operator>(const optional<T>&, const U&);
68   template <class T, class U> constexpr bool operator>(const T&, const optional<U>&);
69   template <class T, class U> constexpr bool operator>=(const optional<T>&, const U&);
70   template <class T, class U> constexpr bool operator>=(const T&, const optional<U>&);
71
72   // 23.6.9, specialized algorithms
73   template <class T> void swap(optional<T>&, optional<T>&) noexcept(see below );
74   template <class T> constexpr optional<see below > make_optional(T&&);
75   template <class T, class... Args>
76     constexpr optional<T> make_optional(Args&&... args);
77   template <class T, class U, class... Args>
78     constexpr optional<T> make_optional(initializer_list<U> il, Args&&... args);
79
80   // 23.6.10, hash support
81   template <class T> struct hash;
82   template <class T> struct hash<optional<T>>;
83
84   template <class T> class optional {
85   public:
86     using value_type = T;
87
88     // 23.6.3.1, constructors
89     constexpr optional() noexcept;
90     constexpr optional(nullopt_t) noexcept;
91     optional(const optional &);
92     optional(optional &&) noexcept(see below);
93     template <class... Args> constexpr explicit optional(in_place_t, Args &&...);
94     template <class U, class... Args>
95       constexpr explicit optional(in_place_t, initializer_list<U>, Args &&...);
96     template <class U = T>
97       constexpr EXPLICIT optional(U &&);
98     template <class U>
99       constexpr EXPLICIT optional(const optional<U> &);
100     template <class U>
101       constexpr EXPLICIT optional(optional<U> &&);
102
103     // 23.6.3.2, destructor
104     ~optional();
105
106     // 23.6.3.3, assignment
107     optional &operator=(nullopt_t) noexcept;
108     optional &operator=(const optional &);                // constexpr in C++20
109     optional &operator=(optional &&) noexcept(see below); // constexpr in C++20
110     template <class U = T> optional &operator=(U &&);
111     template <class U> optional &operator=(const optional<U> &);
112     template <class U> optional &operator=(optional<U> &&);
113     template <class... Args> T& emplace(Args &&...);
114     template <class U, class... Args>
115       T& emplace(initializer_list<U>, Args &&...);
116
117     // 23.6.3.4, swap
118     void swap(optional &) noexcept(see below );
119
120     // 23.6.3.5, observers
121     constexpr T const *operator->() const;
122     constexpr T *operator->();
123     constexpr T const &operator*() const &;
124     constexpr T &operator*() &;
125     constexpr T &&operator*() &&;
126     constexpr const T &&operator*() const &&;
127     constexpr explicit operator bool() const noexcept;
128     constexpr bool has_value() const noexcept;
129     constexpr T const &value() const &;
130     constexpr T &value() &;
131     constexpr T &&value() &&;
132     constexpr const T &&value() const &&;
133     template <class U> constexpr T value_or(U &&) const &;
134     template <class U> constexpr T value_or(U &&) &&;
135
136     // 23.6.3.6, modifiers
137     void reset() noexcept;
138
139   private:
140     T *val; // exposition only
141   };
142
143 template<class T>
144   optional(T) -> optional<T>;
145
146 } // namespace std
147
148 */
149
150 #include <__config>
151 #include <__debug>
152 #include <__functional_base>
153 #include <functional>
154 #include <initializer_list>
155 #include <new>
156 #include <stdexcept>
157 #include <type_traits>
158 #include <utility>
159 #include <version>
160
161 #if !defined(_LIBCPP_HAS_NO_PRAGMA_SYSTEM_HEADER)
162 #pragma GCC system_header
163 #endif
164
165 _LIBCPP_PUSH_MACROS
166 #include <__undef_macros>
167
168
169 namespace std  // purposefully not using versioning namespace
170 {
171
172 class _LIBCPP_EXCEPTION_ABI _LIBCPP_AVAILABILITY_BAD_OPTIONAL_ACCESS bad_optional_access
173     : public exception
174 {
175 public:
176     // Get the key function ~bad_optional_access() into the dylib
177     virtual ~bad_optional_access() _NOEXCEPT;
178     virtual const char* what() const _NOEXCEPT;
179 };
180
181 }  // std
182
183 #if _LIBCPP_STD_VER > 14
184
185 _LIBCPP_BEGIN_NAMESPACE_STD
186
187 _LIBCPP_NORETURN
188 inline _LIBCPP_INLINE_VISIBILITY
189 _LIBCPP_AVAILABILITY_THROW_BAD_OPTIONAL_ACCESS
190 void __throw_bad_optional_access() {
191 #ifndef _LIBCPP_NO_EXCEPTIONS
192         throw bad_optional_access();
193 #else
194         _VSTD::abort();
195 #endif
196 }
197
198 struct nullopt_t
199 {
200     struct __secret_tag { _LIBCPP_INLINE_VISIBILITY explicit __secret_tag() = default; };
201     _LIBCPP_INLINE_VISIBILITY constexpr explicit nullopt_t(__secret_tag, __secret_tag) noexcept {}
202 };
203
204 _LIBCPP_INLINE_VAR constexpr nullopt_t nullopt{nullopt_t::__secret_tag{}, nullopt_t::__secret_tag{}};
205
206 template <class _Tp, bool = is_trivially_destructible<_Tp>::value>
207 struct __optional_destruct_base;
208
209 template <class _Tp>
210 struct __optional_destruct_base<_Tp, false>
211 {
212     typedef _Tp value_type;
213     static_assert(is_object_v<value_type>,
214         "instantiation of optional with a non-object type is undefined behavior");
215     union
216     {
217         char __null_state_;
218         value_type __val_;
219     };
220     bool __engaged_;
221
222     _LIBCPP_INLINE_VISIBILITY
223     ~__optional_destruct_base()
224     {
225         if (__engaged_)
226             __val_.~value_type();
227     }
228
229     _LIBCPP_INLINE_VISIBILITY
230     constexpr __optional_destruct_base() noexcept
231         :  __null_state_(),
232            __engaged_(false) {}
233
234     template <class... _Args>
235     _LIBCPP_INLINE_VISIBILITY
236     constexpr explicit __optional_destruct_base(in_place_t, _Args&&... __args)
237         :  __val_(_VSTD::forward<_Args>(__args)...),
238            __engaged_(true) {}
239
240     _LIBCPP_INLINE_VISIBILITY
241     void reset() noexcept
242     {
243         if (__engaged_)
244         {
245             __val_.~value_type();
246             __engaged_ = false;
247         }
248     }
249 };
250
251 template <class _Tp>
252 struct __optional_destruct_base<_Tp, true>
253 {
254     typedef _Tp value_type;
255     static_assert(is_object_v<value_type>,
256         "instantiation of optional with a non-object type is undefined behavior");
257     union
258     {
259         char __null_state_;
260         value_type __val_;
261     };
262     bool __engaged_;
263
264     _LIBCPP_INLINE_VISIBILITY
265     constexpr __optional_destruct_base() noexcept
266         :  __null_state_(),
267            __engaged_(false) {}
268
269     template <class... _Args>
270     _LIBCPP_INLINE_VISIBILITY
271     constexpr explicit __optional_destruct_base(in_place_t, _Args&&... __args)
272         :  __val_(_VSTD::forward<_Args>(__args)...),
273            __engaged_(true) {}
274
275     _LIBCPP_INLINE_VISIBILITY
276     void reset() noexcept
277     {
278         if (__engaged_)
279         {
280             __engaged_ = false;
281         }
282     }
283 };
284
285 template <class _Tp, bool = is_reference<_Tp>::value>
286 struct __optional_storage_base : __optional_destruct_base<_Tp>
287 {
288     using __base = __optional_destruct_base<_Tp>;
289     using value_type = _Tp;
290     using __base::__base;
291
292     _LIBCPP_INLINE_VISIBILITY
293     constexpr bool has_value() const noexcept
294     {
295         return this->__engaged_;
296     }
297
298     _LIBCPP_INLINE_VISIBILITY
299     constexpr value_type& __get() & noexcept
300     {
301         return this->__val_;
302     }
303     _LIBCPP_INLINE_VISIBILITY
304     constexpr const value_type& __get() const& noexcept
305     {
306         return this->__val_;
307     }
308     _LIBCPP_INLINE_VISIBILITY
309     constexpr value_type&& __get() && noexcept
310     {
311         return _VSTD::move(this->__val_);
312     }
313     _LIBCPP_INLINE_VISIBILITY
314     constexpr const value_type&& __get() const&& noexcept
315     {
316         return _VSTD::move(this->__val_);
317     }
318
319     template <class... _Args>
320     _LIBCPP_INLINE_VISIBILITY
321     void __construct(_Args&&... __args)
322     {
323         _LIBCPP_ASSERT(!has_value(), "__construct called for engaged __optional_storage");
324         ::new((void*)_VSTD::addressof(this->__val_)) value_type(_VSTD::forward<_Args>(__args)...);
325         this->__engaged_ = true;
326     }
327
328     template <class _That>
329     _LIBCPP_INLINE_VISIBILITY
330     void __construct_from(_That&& __opt)
331     {
332         if (__opt.has_value())
333             __construct(_VSTD::forward<_That>(__opt).__get());
334     }
335
336     template <class _That>
337     _LIBCPP_INLINE_VISIBILITY
338     void __assign_from(_That&& __opt)
339     {
340         if (this->__engaged_ == __opt.has_value())
341         {
342             if (this->__engaged_)
343                 this->__val_ = _VSTD::forward<_That>(__opt).__get();
344         }
345         else
346         {
347             if (this->__engaged_)
348                 this->reset();
349             else
350                 __construct(_VSTD::forward<_That>(__opt).__get());
351         }
352     }
353 };
354
355 // optional<T&> is currently required ill-formed, however it may to be in the
356 // future. For this reason it has already been implemented to ensure we can
357 // make the change in an ABI compatible manner.
358 template <class _Tp>
359 struct __optional_storage_base<_Tp, true>
360 {
361     using value_type = _Tp;
362     using __raw_type = remove_reference_t<_Tp>;
363     __raw_type* __value_;
364
365     template <class _Up>
366     static constexpr bool __can_bind_reference() {
367         using _RawUp = typename remove_reference<_Up>::type;
368         using _UpPtr = _RawUp*;
369         using _RawTp = typename remove_reference<_Tp>::type;
370         using _TpPtr = _RawTp*;
371         using _CheckLValueArg = integral_constant<bool,
372             (is_lvalue_reference<_Up>::value && is_convertible<_UpPtr, _TpPtr>::value)
373         ||  is_same<_RawUp, reference_wrapper<_RawTp>>::value
374         ||  is_same<_RawUp, reference_wrapper<typename remove_const<_RawTp>::type>>::value
375         >;
376         return (is_lvalue_reference<_Tp>::value && _CheckLValueArg::value)
377             || (is_rvalue_reference<_Tp>::value && !is_lvalue_reference<_Up>::value &&
378                 is_convertible<_UpPtr, _TpPtr>::value);
379     }
380
381     _LIBCPP_INLINE_VISIBILITY
382     constexpr __optional_storage_base() noexcept
383         :  __value_(nullptr) {}
384
385     template <class _UArg>
386     _LIBCPP_INLINE_VISIBILITY
387     constexpr explicit __optional_storage_base(in_place_t, _UArg&& __uarg)
388         :  __value_(_VSTD::addressof(__uarg))
389     {
390       static_assert(__can_bind_reference<_UArg>(),
391         "Attempted to construct a reference element in tuple from a "
392         "possible temporary");
393     }
394
395     _LIBCPP_INLINE_VISIBILITY
396     void reset() noexcept { __value_ = nullptr; }
397
398     _LIBCPP_INLINE_VISIBILITY
399     constexpr bool has_value() const noexcept
400       { return __value_ != nullptr; }
401
402     _LIBCPP_INLINE_VISIBILITY
403     constexpr value_type& __get() const& noexcept
404       { return *__value_; }
405
406     _LIBCPP_INLINE_VISIBILITY
407     constexpr value_type&& __get() const&& noexcept
408       { return _VSTD::forward<value_type>(*__value_); }
409
410     template <class _UArg>
411     _LIBCPP_INLINE_VISIBILITY
412     void __construct(_UArg&& __val)
413     {
414         _LIBCPP_ASSERT(!has_value(), "__construct called for engaged __optional_storage");
415         static_assert(__can_bind_reference<_UArg>(),
416             "Attempted to construct a reference element in tuple from a "
417             "possible temporary");
418         __value_ = _VSTD::addressof(__val);
419     }
420
421     template <class _That>
422     _LIBCPP_INLINE_VISIBILITY
423     void __construct_from(_That&& __opt)
424     {
425         if (__opt.has_value())
426             __construct(_VSTD::forward<_That>(__opt).__get());
427     }
428
429     template <class _That>
430     _LIBCPP_INLINE_VISIBILITY
431     void __assign_from(_That&& __opt)
432     {
433         if (has_value() == __opt.has_value())
434         {
435             if (has_value())
436                 *__value_ = _VSTD::forward<_That>(__opt).__get();
437         }
438         else
439         {
440             if (has_value())
441                 reset();
442             else
443                 __construct(_VSTD::forward<_That>(__opt).__get());
444         }
445     }
446 };
447
448 template <class _Tp, bool = is_trivially_copy_constructible<_Tp>::value>
449 struct __optional_copy_base : __optional_storage_base<_Tp>
450 {
451     using __optional_storage_base<_Tp>::__optional_storage_base;
452 };
453
454 template <class _Tp>
455 struct __optional_copy_base<_Tp, false> : __optional_storage_base<_Tp>
456 {
457     using __optional_storage_base<_Tp>::__optional_storage_base;
458
459     _LIBCPP_INLINE_VISIBILITY
460     __optional_copy_base() = default;
461
462     _LIBCPP_INLINE_VISIBILITY
463     __optional_copy_base(const __optional_copy_base& __opt)
464     {
465         this->__construct_from(__opt);
466     }
467
468     _LIBCPP_INLINE_VISIBILITY
469     __optional_copy_base(__optional_copy_base&&) = default;
470     _LIBCPP_INLINE_VISIBILITY
471     __optional_copy_base& operator=(const __optional_copy_base&) = default;
472     _LIBCPP_INLINE_VISIBILITY
473     __optional_copy_base& operator=(__optional_copy_base&&) = default;
474 };
475
476 template <class _Tp, bool = is_trivially_move_constructible<_Tp>::value>
477 struct __optional_move_base : __optional_copy_base<_Tp>
478 {
479     using __optional_copy_base<_Tp>::__optional_copy_base;
480 };
481
482 template <class _Tp>
483 struct __optional_move_base<_Tp, false> : __optional_copy_base<_Tp>
484 {
485     using value_type = _Tp;
486     using __optional_copy_base<_Tp>::__optional_copy_base;
487
488     _LIBCPP_INLINE_VISIBILITY
489     __optional_move_base() = default;
490     _LIBCPP_INLINE_VISIBILITY
491     __optional_move_base(const __optional_move_base&) = default;
492
493     _LIBCPP_INLINE_VISIBILITY
494     __optional_move_base(__optional_move_base&& __opt)
495         noexcept(is_nothrow_move_constructible_v<value_type>)
496     {
497         this->__construct_from(_VSTD::move(__opt));
498     }
499
500     _LIBCPP_INLINE_VISIBILITY
501     __optional_move_base& operator=(const __optional_move_base&) = default;
502     _LIBCPP_INLINE_VISIBILITY
503     __optional_move_base& operator=(__optional_move_base&&) = default;
504 };
505
506 template <class _Tp, bool =
507     is_trivially_destructible<_Tp>::value &&
508     is_trivially_copy_constructible<_Tp>::value &&
509     is_trivially_copy_assignable<_Tp>::value>
510 struct __optional_copy_assign_base : __optional_move_base<_Tp>
511 {
512     using __optional_move_base<_Tp>::__optional_move_base;
513 };
514
515 template <class _Tp>
516 struct __optional_copy_assign_base<_Tp, false> : __optional_move_base<_Tp>
517 {
518     using __optional_move_base<_Tp>::__optional_move_base;
519
520     _LIBCPP_INLINE_VISIBILITY
521     __optional_copy_assign_base() = default;
522     _LIBCPP_INLINE_VISIBILITY
523     __optional_copy_assign_base(const __optional_copy_assign_base&) = default;
524     _LIBCPP_INLINE_VISIBILITY
525     __optional_copy_assign_base(__optional_copy_assign_base&&) = default;
526
527     _LIBCPP_INLINE_VISIBILITY
528     __optional_copy_assign_base& operator=(const __optional_copy_assign_base& __opt)
529     {
530         this->__assign_from(__opt);
531         return *this;
532     }
533
534     _LIBCPP_INLINE_VISIBILITY
535     __optional_copy_assign_base& operator=(__optional_copy_assign_base&&) = default;
536 };
537
538 template <class _Tp, bool =
539     is_trivially_destructible<_Tp>::value &&
540     is_trivially_move_constructible<_Tp>::value &&
541     is_trivially_move_assignable<_Tp>::value>
542 struct __optional_move_assign_base : __optional_copy_assign_base<_Tp>
543 {
544     using __optional_copy_assign_base<_Tp>::__optional_copy_assign_base;
545 };
546
547 template <class _Tp>
548 struct __optional_move_assign_base<_Tp, false> : __optional_copy_assign_base<_Tp>
549 {
550     using value_type = _Tp;
551     using __optional_copy_assign_base<_Tp>::__optional_copy_assign_base;
552
553     _LIBCPP_INLINE_VISIBILITY
554     __optional_move_assign_base() = default;
555     _LIBCPP_INLINE_VISIBILITY
556     __optional_move_assign_base(const __optional_move_assign_base& __opt) = default;
557     _LIBCPP_INLINE_VISIBILITY
558     __optional_move_assign_base(__optional_move_assign_base&&) = default;
559     _LIBCPP_INLINE_VISIBILITY
560     __optional_move_assign_base& operator=(const __optional_move_assign_base&) = default;
561
562     _LIBCPP_INLINE_VISIBILITY
563     __optional_move_assign_base& operator=(__optional_move_assign_base&& __opt)
564         noexcept(is_nothrow_move_assignable_v<value_type> &&
565                  is_nothrow_move_constructible_v<value_type>)
566     {
567         this->__assign_from(_VSTD::move(__opt));
568         return *this;
569     }
570 };
571
572 template <class _Tp>
573 using __optional_sfinae_ctor_base_t = __sfinae_ctor_base<
574     is_copy_constructible<_Tp>::value,
575     is_move_constructible<_Tp>::value
576 >;
577
578 template <class _Tp>
579 using __optional_sfinae_assign_base_t = __sfinae_assign_base<
580     (is_copy_constructible<_Tp>::value && is_copy_assignable<_Tp>::value),
581     (is_move_constructible<_Tp>::value && is_move_assignable<_Tp>::value)
582 >;
583
584 template <class _Tp>
585 class optional
586     : private __optional_move_assign_base<_Tp>
587     , private __optional_sfinae_ctor_base_t<_Tp>
588     , private __optional_sfinae_assign_base_t<_Tp>
589 {
590     using __base = __optional_move_assign_base<_Tp>;
591 public:
592     using value_type = _Tp;
593
594 private:
595      // Disable the reference extension using this static assert.
596     static_assert(!is_same_v<value_type, in_place_t>,
597         "instantiation of optional with in_place_t is ill-formed");
598     static_assert(!is_same_v<__uncvref_t<value_type>, nullopt_t>,
599         "instantiation of optional with nullopt_t is ill-formed");
600     static_assert(!is_reference_v<value_type>,
601         "instantiation of optional with a reference type is ill-formed");
602     static_assert(is_destructible_v<value_type>,
603         "instantiation of optional with a non-destructible type is ill-formed");
604
605     // LWG2756: conditionally explicit conversion from _Up
606     struct _CheckOptionalArgsConstructor {
607       template <class _Up>
608       static constexpr bool __enable_implicit() {
609           return is_constructible_v<_Tp, _Up&&> &&
610                  is_convertible_v<_Up&&, _Tp>;
611       }
612
613       template <class _Up>
614       static constexpr bool __enable_explicit() {
615           return is_constructible_v<_Tp, _Up&&> &&
616                  !is_convertible_v<_Up&&, _Tp>;
617       }
618     };
619     template <class _Up>
620     using _CheckOptionalArgsCtor = conditional_t<
621         !is_same_v<__uncvref_t<_Up>, in_place_t> &&
622         !is_same_v<__uncvref_t<_Up>, optional>,
623         _CheckOptionalArgsConstructor,
624         __check_tuple_constructor_fail
625     >;
626     template <class _QualUp>
627     struct _CheckOptionalLikeConstructor {
628       template <class _Up, class _Opt = optional<_Up>>
629       using __check_constructible_from_opt = __lazy_or<
630           is_constructible<_Tp, _Opt&>,
631           is_constructible<_Tp, _Opt const&>,
632           is_constructible<_Tp, _Opt&&>,
633           is_constructible<_Tp, _Opt const&&>,
634           is_convertible<_Opt&, _Tp>,
635           is_convertible<_Opt const&, _Tp>,
636           is_convertible<_Opt&&, _Tp>,
637           is_convertible<_Opt const&&, _Tp>
638       >;
639       template <class _Up, class _Opt = optional<_Up>>
640       using __check_assignable_from_opt = __lazy_or<
641           is_assignable<_Tp&, _Opt&>,
642           is_assignable<_Tp&, _Opt const&>,
643           is_assignable<_Tp&, _Opt&&>,
644           is_assignable<_Tp&, _Opt const&&>
645       >;
646       template <class _Up, class _QUp = _QualUp>
647       static constexpr bool __enable_implicit() {
648           return is_convertible<_QUp, _Tp>::value &&
649               !__check_constructible_from_opt<_Up>::value;
650       }
651       template <class _Up, class _QUp = _QualUp>
652       static constexpr bool __enable_explicit() {
653           return !is_convertible<_QUp, _Tp>::value &&
654               !__check_constructible_from_opt<_Up>::value;
655       }
656       template <class _Up, class _QUp = _QualUp>
657       static constexpr bool __enable_assign() {
658           // Construction and assignability of _Qup to _Tp has already been
659           // checked.
660           return !__check_constructible_from_opt<_Up>::value &&
661               !__check_assignable_from_opt<_Up>::value;
662       }
663     };
664
665     template <class _Up, class _QualUp>
666     using _CheckOptionalLikeCtor = conditional_t<
667       __lazy_and<
668           __lazy_not<is_same<_Up, _Tp>>,
669           is_constructible<_Tp, _QualUp>
670       >::value,
671       _CheckOptionalLikeConstructor<_QualUp>,
672       __check_tuple_constructor_fail
673     >;
674     template <class _Up, class _QualUp>
675     using _CheckOptionalLikeAssign = conditional_t<
676       __lazy_and<
677           __lazy_not<is_same<_Up, _Tp>>,
678           is_constructible<_Tp, _QualUp>,
679           is_assignable<_Tp&, _QualUp>
680       >::value,
681       _CheckOptionalLikeConstructor<_QualUp>,
682       __check_tuple_constructor_fail
683     >;
684 public:
685
686     _LIBCPP_INLINE_VISIBILITY constexpr optional() noexcept {}
687     _LIBCPP_INLINE_VISIBILITY constexpr optional(const optional&) = default;
688     _LIBCPP_INLINE_VISIBILITY constexpr optional(optional&&) = default;
689     _LIBCPP_INLINE_VISIBILITY constexpr optional(nullopt_t) noexcept {}
690
691     template <class... _Args, class = enable_if_t<
692         is_constructible_v<value_type, _Args...>>
693     >
694     _LIBCPP_INLINE_VISIBILITY
695     constexpr explicit optional(in_place_t, _Args&&... __args)
696         : __base(in_place, _VSTD::forward<_Args>(__args)...) {}
697
698     template <class _Up, class... _Args, class = enable_if_t<
699         is_constructible_v<value_type, initializer_list<_Up>&, _Args...>>
700     >
701     _LIBCPP_INLINE_VISIBILITY
702     constexpr explicit optional(in_place_t, initializer_list<_Up> __il, _Args&&... __args)
703         : __base(in_place, __il, _VSTD::forward<_Args>(__args)...) {}
704
705     template <class _Up = value_type, enable_if_t<
706         _CheckOptionalArgsCtor<_Up>::template __enable_implicit<_Up>()
707     , int> = 0>
708     _LIBCPP_INLINE_VISIBILITY
709     constexpr optional(_Up&& __v)
710         : __base(in_place, _VSTD::forward<_Up>(__v)) {}
711
712     template <class _Up, enable_if_t<
713         _CheckOptionalArgsCtor<_Up>::template __enable_explicit<_Up>()
714     , int> = 0>
715     _LIBCPP_INLINE_VISIBILITY
716     constexpr explicit optional(_Up&& __v)
717         : __base(in_place, _VSTD::forward<_Up>(__v)) {}
718
719     // LWG2756: conditionally explicit conversion from const optional<_Up>&
720     template <class _Up, enable_if_t<
721         _CheckOptionalLikeCtor<_Up, _Up const&>::template __enable_implicit<_Up>()
722     , int> = 0>
723     _LIBCPP_INLINE_VISIBILITY
724     optional(const optional<_Up>& __v)
725     {
726         this->__construct_from(__v);
727     }
728     template <class _Up, enable_if_t<
729         _CheckOptionalLikeCtor<_Up, _Up const&>::template __enable_explicit<_Up>()
730     , int> = 0>
731     _LIBCPP_INLINE_VISIBILITY
732     explicit optional(const optional<_Up>& __v)
733     {
734         this->__construct_from(__v);
735     }
736
737     // LWG2756: conditionally explicit conversion from optional<_Up>&&
738     template <class _Up, enable_if_t<
739         _CheckOptionalLikeCtor<_Up, _Up &&>::template __enable_implicit<_Up>()
740     , int> = 0>
741     _LIBCPP_INLINE_VISIBILITY
742     optional(optional<_Up>&& __v)
743     {
744         this->__construct_from(_VSTD::move(__v));
745     }
746     template <class _Up, enable_if_t<
747         _CheckOptionalLikeCtor<_Up, _Up &&>::template __enable_explicit<_Up>()
748     , int> = 0>
749     _LIBCPP_INLINE_VISIBILITY
750     explicit optional(optional<_Up>&& __v)
751     {
752         this->__construct_from(_VSTD::move(__v));
753     }
754
755     _LIBCPP_INLINE_VISIBILITY
756     optional& operator=(nullopt_t) noexcept
757     {
758         reset();
759         return *this;
760     }
761
762     _LIBCPP_INLINE_VISIBILITY optional& operator=(const optional&) = default;
763     _LIBCPP_INLINE_VISIBILITY optional& operator=(optional&&) = default;
764
765     // LWG2756
766     template <class _Up = value_type,
767               class = enable_if_t
768                       <__lazy_and<
769                           integral_constant<bool,
770                               !is_same_v<__uncvref_t<_Up>, optional> &&
771                               !(is_same_v<_Up, value_type> && is_scalar_v<value_type>)
772                           >,
773                           is_constructible<value_type, _Up>,
774                           is_assignable<value_type&, _Up>
775                       >::value>
776              >
777     _LIBCPP_INLINE_VISIBILITY
778     optional&
779     operator=(_Up&& __v)
780     {
781         if (this->has_value())
782             this->__get() = _VSTD::forward<_Up>(__v);
783         else
784             this->__construct(_VSTD::forward<_Up>(__v));
785         return *this;
786     }
787
788     // LWG2756
789     template <class _Up, enable_if_t<
790         _CheckOptionalLikeAssign<_Up, _Up const&>::template __enable_assign<_Up>()
791     , int> = 0>
792     _LIBCPP_INLINE_VISIBILITY
793     optional&
794     operator=(const optional<_Up>& __v)
795     {
796         this->__assign_from(__v);
797         return *this;
798     }
799
800     // LWG2756
801     template <class _Up, enable_if_t<
802         _CheckOptionalLikeCtor<_Up, _Up &&>::template __enable_assign<_Up>()
803     , int> = 0>
804     _LIBCPP_INLINE_VISIBILITY
805     optional&
806     operator=(optional<_Up>&& __v)
807     {
808         this->__assign_from(_VSTD::move(__v));
809         return *this;
810     }
811
812     template <class... _Args,
813               class = enable_if_t
814                       <
815                           is_constructible_v<value_type, _Args...>
816                       >
817              >
818     _LIBCPP_INLINE_VISIBILITY
819     _Tp &
820     emplace(_Args&&... __args)
821     {
822         reset();
823         this->__construct(_VSTD::forward<_Args>(__args)...);
824         return this->__get();
825     }
826
827     template <class _Up, class... _Args,
828               class = enable_if_t
829                       <
830                           is_constructible_v<value_type, initializer_list<_Up>&, _Args...>
831                       >
832              >
833     _LIBCPP_INLINE_VISIBILITY
834     _Tp &
835     emplace(initializer_list<_Up> __il, _Args&&... __args)
836     {
837         reset();
838         this->__construct(__il, _VSTD::forward<_Args>(__args)...);
839         return this->__get();
840     }
841
842     _LIBCPP_INLINE_VISIBILITY
843     void swap(optional& __opt)
844         noexcept(is_nothrow_move_constructible_v<value_type> &&
845                  is_nothrow_swappable_v<value_type>)
846     {
847         if (this->has_value() == __opt.has_value())
848         {
849             using _VSTD::swap;
850             if (this->has_value())
851                 swap(this->__get(), __opt.__get());
852         }
853         else
854         {
855             if (this->has_value())
856             {
857                 __opt.__construct(_VSTD::move(this->__get()));
858                 reset();
859             }
860             else
861             {
862                 this->__construct(_VSTD::move(__opt.__get()));
863                 __opt.reset();
864             }
865         }
866     }
867
868     _LIBCPP_INLINE_VISIBILITY
869     constexpr
870     add_pointer_t<value_type const>
871     operator->() const
872     {
873         _LIBCPP_ASSERT(this->has_value(), "optional operator-> called for disengaged value");
874 #ifndef _LIBCPP_HAS_NO_BUILTIN_ADDRESSOF
875         return _VSTD::addressof(this->__get());
876 #else
877         return __operator_arrow(__has_operator_addressof<value_type>{}, this->__get());
878 #endif
879     }
880
881     _LIBCPP_INLINE_VISIBILITY
882     constexpr
883     add_pointer_t<value_type>
884     operator->()
885     {
886         _LIBCPP_ASSERT(this->has_value(), "optional operator-> called for disengaged value");
887 #ifndef _LIBCPP_HAS_NO_BUILTIN_ADDRESSOF
888         return _VSTD::addressof(this->__get());
889 #else
890         return __operator_arrow(__has_operator_addressof<value_type>{}, this->__get());
891 #endif
892     }
893
894     _LIBCPP_INLINE_VISIBILITY
895     constexpr
896     const value_type&
897     operator*() const&
898     {
899         _LIBCPP_ASSERT(this->has_value(), "optional operator* called for disengaged value");
900         return this->__get();
901     }
902
903     _LIBCPP_INLINE_VISIBILITY
904     constexpr
905     value_type&
906     operator*() &
907     {
908         _LIBCPP_ASSERT(this->has_value(), "optional operator* called for disengaged value");
909         return this->__get();
910     }
911
912     _LIBCPP_INLINE_VISIBILITY
913     constexpr
914     value_type&&
915     operator*() &&
916     {
917         _LIBCPP_ASSERT(this->has_value(), "optional operator* called for disengaged value");
918         return _VSTD::move(this->__get());
919     }
920
921     _LIBCPP_INLINE_VISIBILITY
922     constexpr
923     const value_type&&
924     operator*() const&&
925     {
926         _LIBCPP_ASSERT(this->has_value(), "optional operator* called for disengaged value");
927         return _VSTD::move(this->__get());
928     }
929
930     _LIBCPP_INLINE_VISIBILITY
931     constexpr explicit operator bool() const noexcept { return has_value(); }
932
933     using __base::has_value;
934     using __base::__get;
935
936     _LIBCPP_INLINE_VISIBILITY
937     _LIBCPP_AVAILABILITY_THROW_BAD_OPTIONAL_ACCESS
938     constexpr value_type const& value() const&
939     {
940         if (!this->has_value())
941             __throw_bad_optional_access();
942         return this->__get();
943     }
944
945     _LIBCPP_INLINE_VISIBILITY
946     _LIBCPP_AVAILABILITY_THROW_BAD_OPTIONAL_ACCESS
947     constexpr value_type& value() &
948     {
949         if (!this->has_value())
950             __throw_bad_optional_access();
951         return this->__get();
952     }
953
954     _LIBCPP_INLINE_VISIBILITY
955     _LIBCPP_AVAILABILITY_THROW_BAD_OPTIONAL_ACCESS
956     constexpr value_type&& value() &&
957     {
958         if (!this->has_value())
959             __throw_bad_optional_access();
960         return _VSTD::move(this->__get());
961     }
962
963     _LIBCPP_INLINE_VISIBILITY
964     _LIBCPP_AVAILABILITY_THROW_BAD_OPTIONAL_ACCESS
965     constexpr value_type const&& value() const&&
966     {
967         if (!this->has_value())
968             __throw_bad_optional_access();
969         return _VSTD::move(this->__get());
970     }
971
972     template <class _Up>
973     _LIBCPP_INLINE_VISIBILITY
974     constexpr value_type value_or(_Up&& __v) const&
975     {
976         static_assert(is_copy_constructible_v<value_type>,
977                       "optional<T>::value_or: T must be copy constructible");
978         static_assert(is_convertible_v<_Up, value_type>,
979                       "optional<T>::value_or: U must be convertible to T");
980         return this->has_value() ? this->__get() :
981                                   static_cast<value_type>(_VSTD::forward<_Up>(__v));
982     }
983
984     template <class _Up>
985     _LIBCPP_INLINE_VISIBILITY
986     constexpr value_type value_or(_Up&& __v) &&
987     {
988         static_assert(is_move_constructible_v<value_type>,
989                       "optional<T>::value_or: T must be move constructible");
990         static_assert(is_convertible_v<_Up, value_type>,
991                       "optional<T>::value_or: U must be convertible to T");
992         return this->has_value() ? _VSTD::move(this->__get()) :
993                                   static_cast<value_type>(_VSTD::forward<_Up>(__v));
994     }
995
996     using __base::reset;
997
998 private:
999     template <class _Up>
1000     _LIBCPP_INLINE_VISIBILITY
1001     static _Up*
1002     __operator_arrow(true_type, _Up& __x)
1003     {
1004         return _VSTD::addressof(__x);
1005     }
1006
1007     template <class _Up>
1008     _LIBCPP_INLINE_VISIBILITY
1009     static constexpr _Up*
1010     __operator_arrow(false_type, _Up& __x)
1011     {
1012         return &__x;
1013     }
1014 };
1015
1016 #ifndef _LIBCPP_HAS_NO_DEDUCTION_GUIDES
1017 template<class T>
1018     optional(T) -> optional<T>;
1019 #endif
1020
1021 // Comparisons between optionals
1022 template <class _Tp, class _Up>
1023 _LIBCPP_INLINE_VISIBILITY constexpr
1024 enable_if_t<
1025     is_convertible_v<decltype(_VSTD::declval<const _Tp&>() ==
1026         _VSTD::declval<const _Up&>()), bool>,
1027     bool
1028 >
1029 operator==(const optional<_Tp>& __x, const optional<_Up>& __y)
1030 {
1031     if (static_cast<bool>(__x) != static_cast<bool>(__y))
1032         return false;
1033     if (!static_cast<bool>(__x))
1034         return true;
1035     return *__x == *__y;
1036 }
1037
1038 template <class _Tp, class _Up>
1039 _LIBCPP_INLINE_VISIBILITY constexpr
1040 enable_if_t<
1041     is_convertible_v<decltype(_VSTD::declval<const _Tp&>() !=
1042         _VSTD::declval<const _Up&>()), bool>,
1043     bool
1044 >
1045 operator!=(const optional<_Tp>& __x, const optional<_Up>& __y)
1046 {
1047     if (static_cast<bool>(__x) != static_cast<bool>(__y))
1048         return true;
1049     if (!static_cast<bool>(__x))
1050         return false;
1051     return *__x != *__y;
1052 }
1053
1054 template <class _Tp, class _Up>
1055 _LIBCPP_INLINE_VISIBILITY constexpr
1056 enable_if_t<
1057     is_convertible_v<decltype(_VSTD::declval<const _Tp&>() <
1058         _VSTD::declval<const _Up&>()), bool>,
1059     bool
1060 >
1061 operator<(const optional<_Tp>& __x, const optional<_Up>& __y)
1062 {
1063     if (!static_cast<bool>(__y))
1064         return false;
1065     if (!static_cast<bool>(__x))
1066         return true;
1067     return *__x < *__y;
1068 }
1069
1070 template <class _Tp, class _Up>
1071 _LIBCPP_INLINE_VISIBILITY constexpr
1072 enable_if_t<
1073     is_convertible_v<decltype(_VSTD::declval<const _Tp&>() >
1074         _VSTD::declval<const _Up&>()), bool>,
1075     bool
1076 >
1077 operator>(const optional<_Tp>& __x, const optional<_Up>& __y)
1078 {
1079     if (!static_cast<bool>(__x))
1080         return false;
1081     if (!static_cast<bool>(__y))
1082         return true;
1083     return *__x > *__y;
1084 }
1085
1086 template <class _Tp, class _Up>
1087 _LIBCPP_INLINE_VISIBILITY constexpr
1088 enable_if_t<
1089     is_convertible_v<decltype(_VSTD::declval<const _Tp&>() <=
1090         _VSTD::declval<const _Up&>()), bool>,
1091     bool
1092 >
1093 operator<=(const optional<_Tp>& __x, const optional<_Up>& __y)
1094 {
1095     if (!static_cast<bool>(__x))
1096         return true;
1097     if (!static_cast<bool>(__y))
1098         return false;
1099     return *__x <= *__y;
1100 }
1101
1102 template <class _Tp, class _Up>
1103 _LIBCPP_INLINE_VISIBILITY constexpr
1104 enable_if_t<
1105     is_convertible_v<decltype(_VSTD::declval<const _Tp&>() >=
1106         _VSTD::declval<const _Up&>()), bool>,
1107     bool
1108 >
1109 operator>=(const optional<_Tp>& __x, const optional<_Up>& __y)
1110 {
1111     if (!static_cast<bool>(__y))
1112         return true;
1113     if (!static_cast<bool>(__x))
1114         return false;
1115     return *__x >= *__y;
1116 }
1117
1118 // Comparisons with nullopt
1119 template <class _Tp>
1120 _LIBCPP_INLINE_VISIBILITY constexpr
1121 bool
1122 operator==(const optional<_Tp>& __x, nullopt_t) noexcept
1123 {
1124     return !static_cast<bool>(__x);
1125 }
1126
1127 template <class _Tp>
1128 _LIBCPP_INLINE_VISIBILITY constexpr
1129 bool
1130 operator==(nullopt_t, const optional<_Tp>& __x) noexcept
1131 {
1132     return !static_cast<bool>(__x);
1133 }
1134
1135 template <class _Tp>
1136 _LIBCPP_INLINE_VISIBILITY constexpr
1137 bool
1138 operator!=(const optional<_Tp>& __x, nullopt_t) noexcept
1139 {
1140     return static_cast<bool>(__x);
1141 }
1142
1143 template <class _Tp>
1144 _LIBCPP_INLINE_VISIBILITY constexpr
1145 bool
1146 operator!=(nullopt_t, const optional<_Tp>& __x) noexcept
1147 {
1148     return static_cast<bool>(__x);
1149 }
1150
1151 template <class _Tp>
1152 _LIBCPP_INLINE_VISIBILITY constexpr
1153 bool
1154 operator<(const optional<_Tp>&, nullopt_t) noexcept
1155 {
1156     return false;
1157 }
1158
1159 template <class _Tp>
1160 _LIBCPP_INLINE_VISIBILITY constexpr
1161 bool
1162 operator<(nullopt_t, const optional<_Tp>& __x) noexcept
1163 {
1164     return static_cast<bool>(__x);
1165 }
1166
1167 template <class _Tp>
1168 _LIBCPP_INLINE_VISIBILITY constexpr
1169 bool
1170 operator<=(const optional<_Tp>& __x, nullopt_t) noexcept
1171 {
1172     return !static_cast<bool>(__x);
1173 }
1174
1175 template <class _Tp>
1176 _LIBCPP_INLINE_VISIBILITY constexpr
1177 bool
1178 operator<=(nullopt_t, const optional<_Tp>&) noexcept
1179 {
1180     return true;
1181 }
1182
1183 template <class _Tp>
1184 _LIBCPP_INLINE_VISIBILITY constexpr
1185 bool
1186 operator>(const optional<_Tp>& __x, nullopt_t) noexcept
1187 {
1188     return static_cast<bool>(__x);
1189 }
1190
1191 template <class _Tp>
1192 _LIBCPP_INLINE_VISIBILITY constexpr
1193 bool
1194 operator>(nullopt_t, const optional<_Tp>&) noexcept
1195 {
1196     return false;
1197 }
1198
1199 template <class _Tp>
1200 _LIBCPP_INLINE_VISIBILITY constexpr
1201 bool
1202 operator>=(const optional<_Tp>&, nullopt_t) noexcept
1203 {
1204     return true;
1205 }
1206
1207 template <class _Tp>
1208 _LIBCPP_INLINE_VISIBILITY constexpr
1209 bool
1210 operator>=(nullopt_t, const optional<_Tp>& __x) noexcept
1211 {
1212     return !static_cast<bool>(__x);
1213 }
1214
1215 // Comparisons with T
1216 template <class _Tp, class _Up>
1217 _LIBCPP_INLINE_VISIBILITY constexpr
1218 enable_if_t<
1219     is_convertible_v<decltype(_VSTD::declval<const _Tp&>() ==
1220         _VSTD::declval<const _Up&>()), bool>,
1221     bool
1222 >
1223 operator==(const optional<_Tp>& __x, const _Up& __v)
1224 {
1225     return static_cast<bool>(__x) ? *__x == __v : false;
1226 }
1227
1228 template <class _Tp, class _Up>
1229 _LIBCPP_INLINE_VISIBILITY constexpr
1230 enable_if_t<
1231     is_convertible_v<decltype(_VSTD::declval<const _Tp&>() ==
1232         _VSTD::declval<const _Up&>()), bool>,
1233     bool
1234 >
1235 operator==(const _Tp& __v, const optional<_Up>& __x)
1236 {
1237     return static_cast<bool>(__x) ? __v == *__x : false;
1238 }
1239
1240 template <class _Tp, class _Up>
1241 _LIBCPP_INLINE_VISIBILITY constexpr
1242 enable_if_t<
1243     is_convertible_v<decltype(_VSTD::declval<const _Tp&>() !=
1244         _VSTD::declval<const _Up&>()), bool>,
1245     bool
1246 >
1247 operator!=(const optional<_Tp>& __x, const _Up& __v)
1248 {
1249     return static_cast<bool>(__x) ? *__x != __v : true;
1250 }
1251
1252 template <class _Tp, class _Up>
1253 _LIBCPP_INLINE_VISIBILITY constexpr
1254 enable_if_t<
1255     is_convertible_v<decltype(_VSTD::declval<const _Tp&>() !=
1256         _VSTD::declval<const _Up&>()), bool>,
1257     bool
1258 >
1259 operator!=(const _Tp& __v, const optional<_Up>& __x)
1260 {
1261     return static_cast<bool>(__x) ? __v != *__x : true;
1262 }
1263
1264 template <class _Tp, class _Up>
1265 _LIBCPP_INLINE_VISIBILITY constexpr
1266 enable_if_t<
1267     is_convertible_v<decltype(_VSTD::declval<const _Tp&>() <
1268         _VSTD::declval<const _Up&>()), bool>,
1269     bool
1270 >
1271 operator<(const optional<_Tp>& __x, const _Up& __v)
1272 {
1273     return static_cast<bool>(__x) ? *__x < __v : true;
1274 }
1275
1276 template <class _Tp, class _Up>
1277 _LIBCPP_INLINE_VISIBILITY constexpr
1278 enable_if_t<
1279     is_convertible_v<decltype(_VSTD::declval<const _Tp&>() <
1280         _VSTD::declval<const _Up&>()), bool>,
1281     bool
1282 >
1283 operator<(const _Tp& __v, const optional<_Up>& __x)
1284 {
1285     return static_cast<bool>(__x) ? __v < *__x : false;
1286 }
1287
1288 template <class _Tp, class _Up>
1289 _LIBCPP_INLINE_VISIBILITY constexpr
1290 enable_if_t<
1291     is_convertible_v<decltype(_VSTD::declval<const _Tp&>() <=
1292         _VSTD::declval<const _Up&>()), bool>,
1293     bool
1294 >
1295 operator<=(const optional<_Tp>& __x, const _Up& __v)
1296 {
1297     return static_cast<bool>(__x) ? *__x <= __v : true;
1298 }
1299
1300 template <class _Tp, class _Up>
1301 _LIBCPP_INLINE_VISIBILITY constexpr
1302 enable_if_t<
1303     is_convertible_v<decltype(_VSTD::declval<const _Tp&>() <=
1304         _VSTD::declval<const _Up&>()), bool>,
1305     bool
1306 >
1307 operator<=(const _Tp& __v, const optional<_Up>& __x)
1308 {
1309     return static_cast<bool>(__x) ? __v <= *__x : false;
1310 }
1311
1312 template <class _Tp, class _Up>
1313 _LIBCPP_INLINE_VISIBILITY constexpr
1314 enable_if_t<
1315     is_convertible_v<decltype(_VSTD::declval<const _Tp&>() >
1316         _VSTD::declval<const _Up&>()), bool>,
1317     bool
1318 >
1319 operator>(const optional<_Tp>& __x, const _Up& __v)
1320 {
1321     return static_cast<bool>(__x) ? *__x > __v : false;
1322 }
1323
1324 template <class _Tp, class _Up>
1325 _LIBCPP_INLINE_VISIBILITY constexpr
1326 enable_if_t<
1327     is_convertible_v<decltype(_VSTD::declval<const _Tp&>() >
1328         _VSTD::declval<const _Up&>()), bool>,
1329     bool
1330 >
1331 operator>(const _Tp& __v, const optional<_Up>& __x)
1332 {
1333     return static_cast<bool>(__x) ? __v > *__x : true;
1334 }
1335
1336 template <class _Tp, class _Up>
1337 _LIBCPP_INLINE_VISIBILITY constexpr
1338 enable_if_t<
1339     is_convertible_v<decltype(_VSTD::declval<const _Tp&>() >=
1340         _VSTD::declval<const _Up&>()), bool>,
1341     bool
1342 >
1343 operator>=(const optional<_Tp>& __x, const _Up& __v)
1344 {
1345     return static_cast<bool>(__x) ? *__x >= __v : false;
1346 }
1347
1348 template <class _Tp, class _Up>
1349 _LIBCPP_INLINE_VISIBILITY constexpr
1350 enable_if_t<
1351     is_convertible_v<decltype(_VSTD::declval<const _Tp&>() >=
1352         _VSTD::declval<const _Up&>()), bool>,
1353     bool
1354 >
1355 operator>=(const _Tp& __v, const optional<_Up>& __x)
1356 {
1357     return static_cast<bool>(__x) ? __v >= *__x : true;
1358 }
1359
1360
1361 template <class _Tp>
1362 inline _LIBCPP_INLINE_VISIBILITY
1363 enable_if_t<
1364     is_move_constructible_v<_Tp> && is_swappable_v<_Tp>,
1365     void
1366 >
1367 swap(optional<_Tp>& __x, optional<_Tp>& __y) noexcept(noexcept(__x.swap(__y)))
1368 {
1369     __x.swap(__y);
1370 }
1371
1372 template <class _Tp>
1373 _LIBCPP_INLINE_VISIBILITY constexpr
1374 optional<decay_t<_Tp>> make_optional(_Tp&& __v)
1375 {
1376     return optional<decay_t<_Tp>>(_VSTD::forward<_Tp>(__v));
1377 }
1378
1379 template <class _Tp, class... _Args>
1380 _LIBCPP_INLINE_VISIBILITY constexpr
1381 optional<_Tp> make_optional(_Args&&... __args)
1382 {
1383     return optional<_Tp>(in_place, _VSTD::forward<_Args>(__args)...);
1384 }
1385
1386 template <class _Tp, class _Up, class... _Args>
1387 _LIBCPP_INLINE_VISIBILITY constexpr
1388 optional<_Tp> make_optional(initializer_list<_Up> __il,  _Args&&... __args)
1389 {
1390     return optional<_Tp>(in_place, __il, _VSTD::forward<_Args>(__args)...);
1391 }
1392
1393 template <class _Tp>
1394 struct _LIBCPP_TEMPLATE_VIS hash<
1395     __enable_hash_helper<optional<_Tp>, remove_const_t<_Tp>>
1396 >
1397 {
1398     typedef optional<_Tp> argument_type;
1399     typedef size_t        result_type;
1400
1401     _LIBCPP_INLINE_VISIBILITY
1402     result_type operator()(const argument_type& __opt) const
1403     {
1404         return static_cast<bool>(__opt) ? hash<remove_const_t<_Tp>>()(*__opt) : 0;
1405     }
1406 };
1407
1408 _LIBCPP_END_NAMESPACE_STD
1409
1410 #endif  // _LIBCPP_STD_VER > 14
1411
1412 _LIBCPP_POP_MACROS
1413
1414 #endif  // _LIBCPP_OPTIONAL