NS-3 based Named Data Networking (NDN) simulator
ndnSIM 2.5: NDN, CCN, CCNx, content centric networks
API Documentation
optional.hpp
Go to the documentation of this file.
1 //
2 // Copyright (c) 2014-2018 Martin Moene
3 //
4 // https://github.com/martinmoene/optional-lite
5 //
6 // Distributed under the Boost Software License, Version 1.0.
7 // (See accompanying file LICENSE.txt or copy at http://www.boost.org/LICENSE_1_0.txt)
8 
9 #pragma once
10 
11 #ifndef NONSTD_OPTIONAL_LITE_HPP
12 #define NONSTD_OPTIONAL_LITE_HPP
13 
14 #define optional_lite_MAJOR 3
15 #define optional_lite_MINOR 1
16 #define optional_lite_PATCH 1
17 
18 #define optional_lite_VERSION optional_STRINGIFY(optional_lite_MAJOR) "." optional_STRINGIFY(optional_lite_MINOR) "." optional_STRINGIFY(optional_lite_PATCH)
19 
20 #define optional_STRINGIFY( x ) optional_STRINGIFY_( x )
21 #define optional_STRINGIFY_( x ) #x
22 
23 // optional-lite configuration:
24 
25 #define optional_OPTIONAL_DEFAULT 0
26 #define optional_OPTIONAL_NONSTD 1
27 #define optional_OPTIONAL_STD 2
28 
29 #if !defined( optional_CONFIG_SELECT_OPTIONAL )
30 # define optional_CONFIG_SELECT_OPTIONAL ( optional_HAVE_STD_OPTIONAL ? optional_OPTIONAL_STD : optional_OPTIONAL_NONSTD )
31 #endif
32 
33 // C++ language version detection (C++20 is speculative):
34 // Note: VC14.0/1900 (VS2015) lacks too much from C++14.
35 
36 #ifndef optional_CPLUSPLUS
37 # if defined(_MSVC_LANG ) && !defined(__clang__)
38 # define optional_CPLUSPLUS (_MSC_VER == 1900 ? 201103L : _MSVC_LANG )
39 # else
40 # define optional_CPLUSPLUS __cplusplus
41 # endif
42 #endif
43 
44 #define optional_CPP98_OR_GREATER ( optional_CPLUSPLUS >= 199711L )
45 #define optional_CPP11_OR_GREATER ( optional_CPLUSPLUS >= 201103L )
46 #define optional_CPP11_OR_GREATER_ ( optional_CPLUSPLUS >= 201103L )
47 #define optional_CPP14_OR_GREATER ( optional_CPLUSPLUS >= 201402L )
48 #define optional_CPP17_OR_GREATER ( optional_CPLUSPLUS >= 201703L )
49 #define optional_CPP20_OR_GREATER ( optional_CPLUSPLUS >= 202000L )
50 
51 // C++ language version (represent 98 as 3):
52 
53 #define optional_CPLUSPLUS_V ( optional_CPLUSPLUS / 100 - (optional_CPLUSPLUS > 200000 ? 2000 : 1994) )
54 
55 // Use C++17 std::optional if available and requested:
56 
57 #if optional_CPP17_OR_GREATER && defined(__has_include )
58 # if __has_include( <optional> )
59 # define optional_HAVE_STD_OPTIONAL 1
60 # else
61 # define optional_HAVE_STD_OPTIONAL 0
62 # endif
63 #else
64 # define optional_HAVE_STD_OPTIONAL 0
65 #endif
66 
67 #define optional_USES_STD_OPTIONAL ( (optional_CONFIG_SELECT_OPTIONAL == optional_OPTIONAL_STD) || ((optional_CONFIG_SELECT_OPTIONAL == optional_OPTIONAL_DEFAULT) && optional_HAVE_STD_OPTIONAL) )
68 
69 //
70 // in_place: code duplicated in any-lite, expected-lite, optional-lite, value-ptr-lite, variant-lite:
71 //
72 
73 #ifndef nonstd_lite_HAVE_IN_PLACE_TYPES
74 #define nonstd_lite_HAVE_IN_PLACE_TYPES 1
75 
76 // C++17 std::in_place in <utility>:
77 
78 #if optional_CPP17_OR_GREATER
79 
80 #include <utility>
81 
82 namespace nonstd {
83 
84 using std::in_place;
85 using std::in_place_type;
87 using std::in_place_t;
88 using std::in_place_type_t;
89 using std::in_place_index_t;
90 
91 #define nonstd_lite_in_place_t( T) std::in_place_t
92 #define nonstd_lite_in_place_type_t( T) std::in_place_type_t<T>
93 #define nonstd_lite_in_place_index_t(K) std::in_place_index_t<K>
94 
95 #define nonstd_lite_in_place( T) std::in_place_t{}
96 #define nonstd_lite_in_place_type( T) std::in_place_type_t<T>{}
97 #define nonstd_lite_in_place_index(K) std::in_place_index_t<K>{}
98 
99 } // namespace nonstd
100 
101 #else // optional_CPP17_OR_GREATER
102 
103 #include <cstddef>
104 
105 namespace nonstd {
106 namespace detail {
107 
108 template< class T >
109 struct in_place_type_tag {};
110 
111 template< std::size_t K >
112 struct in_place_index_tag {};
113 
114 } // namespace detail
115 
116 struct in_place_t {};
117 
118 template< class T >
119 inline in_place_t in_place( detail::in_place_type_tag<T> = detail::in_place_type_tag<T>() )
120 {
121  return in_place_t();
122 }
123 
124 template< std::size_t K >
125 inline in_place_t in_place( detail::in_place_index_tag<K> = detail::in_place_index_tag<K>() )
126 {
127  return in_place_t();
128 }
129 
130 template< class T >
131 inline in_place_t in_place_type( detail::in_place_type_tag<T> = detail::in_place_type_tag<T>() )
132 {
133  return in_place_t();
134 }
135 
136 template< std::size_t K >
137 inline in_place_t in_place_index( detail::in_place_index_tag<K> = detail::in_place_index_tag<K>() )
138 {
139  return in_place_t();
140 }
141 
142 // mimic templated typedef:
143 
144 #define nonstd_lite_in_place_t( T) nonstd::in_place_t(&)( nonstd::detail::in_place_type_tag<T> )
145 #define nonstd_lite_in_place_type_t( T) nonstd::in_place_t(&)( nonstd::detail::in_place_type_tag<T> )
146 #define nonstd_lite_in_place_index_t(K) nonstd::in_place_t(&)( nonstd::detail::in_place_index_tag<K> )
147 
148 #define nonstd_lite_in_place( T) nonstd::in_place_type<T>
149 #define nonstd_lite_in_place_type( T) nonstd::in_place_type<T>
150 #define nonstd_lite_in_place_index(K) nonstd::in_place_index<K>
151 
152 } // namespace nonstd
153 
154 #endif // optional_CPP17_OR_GREATER
155 #endif // nonstd_lite_HAVE_IN_PLACE_TYPES
156 
157 //
158 // Using std::optional:
159 //
160 
161 #if optional_USES_STD_OPTIONAL
162 
163 #include <optional>
164 
165 namespace nonstd {
166 
167  using std::optional;
168  using std::bad_optional_access;
169  using std::hash;
170 
171  using std::nullopt;
172  using std::nullopt_t;
173 
174  using std::operator==;
175  using std::operator!=;
176  using std::operator<;
177  using std::operator<=;
178  using std::operator>;
179  using std::operator>=;
180  using std::make_optional;
181  using std::swap;
182 }
183 
184 #else // optional_USES_STD_OPTIONAL
185 
186 #include <cassert>
187 #include <stdexcept>
188 #include <utility>
189 
190 // optional-lite alignment configuration:
191 
192 #ifndef optional_CONFIG_MAX_ALIGN_HACK
193 # define optional_CONFIG_MAX_ALIGN_HACK 0
194 #endif
195 
196 #ifndef optional_CONFIG_ALIGN_AS
197 // no default, used in #if defined()
198 #endif
199 
200 #ifndef optional_CONFIG_ALIGN_AS_FALLBACK
201 # define optional_CONFIG_ALIGN_AS_FALLBACK double
202 #endif
203 
204 // Compiler warning suppression:
205 
206 #if defined(__clang__)
207 # pragma clang diagnostic push
208 # pragma clang diagnostic ignored "-Wundef"
209 #elif defined(__GNUC__)
210 # pragma GCC diagnostic push
211 # pragma GCC diagnostic ignored "-Wundef"
212 #endif
213 
214 // half-open range [lo..hi):
215 #define optional_BETWEEN( v, lo, hi ) ( (lo) <= (v) && (v) < (hi) )
216 
217 // Compiler versions:
218 //
219 // MSVC++ 6.0 _MSC_VER == 1200 (Visual Studio 6.0)
220 // MSVC++ 7.0 _MSC_VER == 1300 (Visual Studio .NET 2002)
221 // MSVC++ 7.1 _MSC_VER == 1310 (Visual Studio .NET 2003)
222 // MSVC++ 8.0 _MSC_VER == 1400 (Visual Studio 2005)
223 // MSVC++ 9.0 _MSC_VER == 1500 (Visual Studio 2008)
224 // MSVC++ 10.0 _MSC_VER == 1600 (Visual Studio 2010)
225 // MSVC++ 11.0 _MSC_VER == 1700 (Visual Studio 2012)
226 // MSVC++ 12.0 _MSC_VER == 1800 (Visual Studio 2013)
227 // MSVC++ 14.0 _MSC_VER == 1900 (Visual Studio 2015)
228 // MSVC++ 14.1 _MSC_VER >= 1910 (Visual Studio 2017)
229 
230 #if defined(_MSC_VER ) && !defined(__clang__)
231 # define optional_COMPILER_MSVC_VER (_MSC_VER )
232 # define optional_COMPILER_MSVC_VERSION (_MSC_VER / 10 - 10 * ( 5 + (_MSC_VER < 1900 ) ) )
233 #else
234 # define optional_COMPILER_MSVC_VER 0
235 # define optional_COMPILER_MSVC_VERSION 0
236 #endif
237 
238 #define optional_COMPILER_VERSION( major, minor, patch ) ( 10 * (10 * major + minor ) + patch )
239 
240 #if defined(__GNUC__) && !defined(__clang__)
241 # define optional_COMPILER_GNUC_VERSION optional_COMPILER_VERSION(__GNUC__, __GNUC_MINOR__, __GNUC_PATCHLEVEL__)
242 #else
243 # define optional_COMPILER_GNUC_VERSION 0
244 #endif
245 
246 #if defined(__clang__)
247 # define optional_COMPILER_CLANG_VERSION optional_COMPILER_VERSION(__clang_major__, __clang_minor__, __clang_patchlevel__)
248 #else
249 # define optional_COMPILER_CLANG_VERSION 0
250 #endif
251 
252 #if optional_BETWEEN(optional_COMPILER_MSVC_VERSION, 70, 140 )
253 # pragma warning( push )
254 # pragma warning( disable: 4345 ) // initialization behavior changed
255 #endif
256 
257 #if optional_BETWEEN(optional_COMPILER_MSVC_VERSION, 70, 150 )
258 # pragma warning( push )
259 # pragma warning( disable: 4814 ) // in C++14 'constexpr' will not imply 'const'
260 #endif
261 
262 // Presence of language and library features:
263 
264 #define optional_HAVE(FEATURE) ( optional_HAVE_##FEATURE )
265 
266 #ifdef _HAS_CPP0X
267 # define optional_HAS_CPP0X _HAS_CPP0X
268 #else
269 # define optional_HAS_CPP0X 0
270 #endif
271 
272 // Unless defined otherwise below, consider VC14 as C++11 for optional-lite:
273 
274 #if optional_COMPILER_MSVC_VER >= 1900
275 # undef optional_CPP11_OR_GREATER
276 # define optional_CPP11_OR_GREATER 1
277 #endif
278 
279 #define optional_CPP11_90 (optional_CPP11_OR_GREATER_ || optional_COMPILER_MSVC_VER >= 1500)
280 #define optional_CPP11_100 (optional_CPP11_OR_GREATER_ || optional_COMPILER_MSVC_VER >= 1600)
281 #define optional_CPP11_110 (optional_CPP11_OR_GREATER_ || optional_COMPILER_MSVC_VER >= 1700)
282 #define optional_CPP11_120 (optional_CPP11_OR_GREATER_ || optional_COMPILER_MSVC_VER >= 1800)
283 #define optional_CPP11_140 (optional_CPP11_OR_GREATER_ || optional_COMPILER_MSVC_VER >= 1900)
284 #define optional_CPP11_141 (optional_CPP11_OR_GREATER_ || optional_COMPILER_MSVC_VER >= 1910)
285 
286 #define optional_CPP14_000 (optional_CPP14_OR_GREATER)
287 #define optional_CPP17_000 (optional_CPP17_OR_GREATER)
288 
289 // Presence of C++11 language features:
290 
291 #define optional_HAVE_CONSTEXPR_11 optional_CPP11_140
292 #define optional_HAVE_NOEXCEPT optional_CPP11_140
293 #define optional_HAVE_NULLPTR optional_CPP11_100
294 #define optional_HAVE_REF_QUALIFIER optional_CPP11_140
295 
296 // Presence of C++14 language features:
297 
298 #define optional_HAVE_CONSTEXPR_14 optional_CPP14_000
299 
300 // Presence of C++17 language features:
301 
302 // no flag
303 
304 // Presence of C++ library features:
305 
306 #define optional_HAVE_CONDITIONAL optional_CPP11_120
307 #define optional_HAVE_REMOVE_CV optional_CPP11_120
308 #define optional_HAVE_TYPE_TRAITS optional_CPP11_90
309 
310 #define optional_HAVE_TR1_TYPE_TRAITS (!! optional_COMPILER_GNUC_VERSION )
311 #define optional_HAVE_TR1_ADD_POINTER (!! optional_COMPILER_GNUC_VERSION )
312 
313 // C++ feature usage:
314 
315 #if optional_HAVE( CONSTEXPR_11 )
316 # define optional_constexpr constexpr
317 #else
318 # define optional_constexpr /*constexpr*/
319 #endif
320 
321 #if optional_HAVE( CONSTEXPR_14 )
322 # define optional_constexpr14 constexpr
323 #else
324 # define optional_constexpr14 /*constexpr*/
325 #endif
326 
327 #if optional_HAVE( NOEXCEPT )
328 # define optional_noexcept noexcept
329 #else
330 # define optional_noexcept /*noexcept*/
331 #endif
332 
333 #if optional_HAVE( NULLPTR )
334 # define optional_nullptr nullptr
335 #else
336 # define optional_nullptr NULL
337 #endif
338 
339 #if optional_HAVE( REF_QUALIFIER )
340 # define optional_ref_qual &
341 # define optional_refref_qual &&
342 #else
343 # define optional_ref_qual /*&*/
344 # define optional_refref_qual /*&&*/
345 #endif
346 
347 // additional includes:
348 
349 #if optional_CPP11_OR_GREATER
350 # include <functional>
351 #endif
352 
353 #if optional_HAVE( INITIALIZER_LIST )
354 # include <initializer_list>
355 #endif
356 
357 #if optional_HAVE( TYPE_TRAITS )
358 # include <type_traits>
359 #elif optional_HAVE( TR1_TYPE_TRAITS )
360 # include <tr1/type_traits>
361 #endif
362 
363 // Method enabling
364 
365 #if optional_CPP11_OR_GREATER
366 
367 # define optional_REQUIRES_T(...) \
368  , typename = typename std::enable_if<__VA_ARGS__>::type
369 
370 # define optional_REQUIRES_R(R, ...) \
371  typename std::enable_if<__VA_ARGS__, R>::type
372 
373 # define optional_REQUIRES_A(...) \
374  , typename std::enable_if<__VA_ARGS__, void*>::type = optional_nullptr
375 
376 #endif
377 
378 //
379 // optional:
380 //
381 
382 namespace nonstd { namespace optional_lite {
383 
384 namespace detail {
385 
386 #if optional_HAVE( CONDITIONAL )
387  using std::conditional;
388 #else
389  template< bool B, typename T, typename F > struct conditional { typedef T type; };
390  template< typename T, typename F > struct conditional<false, T, F> { typedef F type; };
391 #endif // optional_HAVE_CONDITIONAL
392 
393 } // namespace detail
394 
395 #if optional_CPP11_OR_GREATER
396 
397 namespace std20 {
398 
399 // type traits C++20:
400 
401 template< typename T >
402 struct remove_cvref
403 {
404  typedef typename std::remove_cv< typename std::remove_reference<T>::type >::type type;
405 };
406 
407 } // namespace std20
408 
409 #endif // optional_CPP11_OR_GREATER
410 
412 
413 template< typename T >
414 class optional;
415 
416 namespace detail {
417 
418 // C++11 emulation:
419 
420 struct nulltype{};
421 
422 template< typename Head, typename Tail >
423 struct typelist
424 {
425  typedef Head head;
426  typedef Tail tail;
427 };
428 
429 #if optional_CONFIG_MAX_ALIGN_HACK
430 
431 // Max align, use most restricted type for alignment:
432 
433 #define optional_UNIQUE( name ) optional_UNIQUE2( name, __LINE__ )
434 #define optional_UNIQUE2( name, line ) optional_UNIQUE3( name, line )
435 #define optional_UNIQUE3( name, line ) name ## line
436 
437 #define optional_ALIGN_TYPE( type ) \
438  type optional_UNIQUE( _t ); struct_t< type > optional_UNIQUE( _st )
439 
440 template< typename T >
441 struct struct_t { T _; };
442 
443 union max_align_t
444 {
445  optional_ALIGN_TYPE( char );
446  optional_ALIGN_TYPE( short int );
447  optional_ALIGN_TYPE( int );
448  optional_ALIGN_TYPE( long int );
449  optional_ALIGN_TYPE( float );
450  optional_ALIGN_TYPE( double );
451  optional_ALIGN_TYPE( long double );
452  optional_ALIGN_TYPE( char * );
453  optional_ALIGN_TYPE( short int * );
454  optional_ALIGN_TYPE( int * );
455  optional_ALIGN_TYPE( long int * );
456  optional_ALIGN_TYPE( float * );
457  optional_ALIGN_TYPE( double * );
458  optional_ALIGN_TYPE( long double * );
459  optional_ALIGN_TYPE( void * );
460 
461 #ifdef HAVE_LONG_LONG
462  optional_ALIGN_TYPE( long long );
463 #endif
464 
465  struct Unknown;
466 
467  Unknown ( * optional_UNIQUE(_) )( Unknown );
468  Unknown * Unknown::* optional_UNIQUE(_);
469  Unknown ( Unknown::* optional_UNIQUE(_) )( Unknown );
470 
471  struct_t< Unknown ( * )( Unknown) > optional_UNIQUE(_);
472  struct_t< Unknown * Unknown::* > optional_UNIQUE(_);
473  struct_t< Unknown ( Unknown::* )(Unknown) > optional_UNIQUE(_);
474 };
475 
476 #undef optional_UNIQUE
477 #undef optional_UNIQUE2
478 #undef optional_UNIQUE3
479 
480 #undef optional_ALIGN_TYPE
481 
482 #elif defined( optional_CONFIG_ALIGN_AS ) // optional_CONFIG_MAX_ALIGN_HACK
483 
484 // Use user-specified type for alignment:
485 
486 #define optional_ALIGN_AS( unused ) \
487  optional_CONFIG_ALIGN_AS
488 
489 #else // optional_CONFIG_MAX_ALIGN_HACK
490 
491 // Determine POD type to use for alignment:
492 
493 #define optional_ALIGN_AS( to_align ) \
494  typename type_of_size< alignment_types, alignment_of< to_align >::value >::type
495 
496 template< typename T >
498 
499 template< typename T >
501 {
502  char c;
503  T t;
505 };
506 
507 template< size_t A, size_t S >
509 {
510  enum { value = A < S ? A : S };
511 };
512 
513 template< typename T >
514 struct alignment_of
515 {
517  sizeof( alignment_of_hack<T> ) - sizeof(T), sizeof(T) >::value };
518 };
519 
520 template< typename List, size_t N >
522 {
523  typedef typename conditional<
524  N == sizeof( typename List::head ),
525  typename List::head,
527 };
528 
529 template< size_t N >
530 struct type_of_size< nulltype, N >
531 {
533 };
534 
535 template< typename T>
536 struct struct_t { T _; };
537 
538 #define optional_ALIGN_TYPE( type ) \
539  typelist< type , typelist< struct_t< type >
540 
541 struct Unknown;
542 
543 typedef
544  optional_ALIGN_TYPE( char ),
545  optional_ALIGN_TYPE( short ),
546  optional_ALIGN_TYPE( int ),
547  optional_ALIGN_TYPE( long ),
548  optional_ALIGN_TYPE( float ),
549  optional_ALIGN_TYPE( double ),
550  optional_ALIGN_TYPE( long double ),
551 
552  optional_ALIGN_TYPE( char *),
553  optional_ALIGN_TYPE( short * ),
554  optional_ALIGN_TYPE( int * ),
555  optional_ALIGN_TYPE( long * ),
556  optional_ALIGN_TYPE( float * ),
557  optional_ALIGN_TYPE( double * ),
558  optional_ALIGN_TYPE( long double * ),
559 
560  optional_ALIGN_TYPE( Unknown ( * )( Unknown ) ),
561  optional_ALIGN_TYPE( Unknown * Unknown::* ),
562  optional_ALIGN_TYPE( Unknown ( Unknown::* )( Unknown ) ),
563 
564  nulltype
565  > > > > > > > > > > > > > >
566  > > > > > > > > > > > > > >
567  > > > > > >
569 
570 #undef optional_ALIGN_TYPE
571 
572 #endif // optional_CONFIG_MAX_ALIGN_HACK
573 
575 
576 template< typename T >
578 {
579 //private:
580 // template< typename > friend class optional;
581 
582  typedef T value_type;
583 
585 
586  storage_t( value_type const & v )
587  {
588  construct_value( v );
589  }
590 
591  void construct_value( value_type const & v )
592  {
593  ::new( value_ptr() ) value_type( v );
594  }
595 
596 #if optional_CPP11_OR_GREATER
597 
598  storage_t( value_type && v )
599  {
600  construct_value( std::move( v ) );
601  }
602 
603  void construct_value( value_type && v )
604  {
605  ::new( value_ptr() ) value_type( std::move( v ) );
606  }
607 
608  template< class... Args >
609  void emplace( Args&&... args )
610  {
611  ::new( value_ptr() ) value_type( std::forward<Args>(args)... );
612  }
613 
614  template< class U, class... Args >
615  void emplace( std::initializer_list<U> il, Args&&... args )
616  {
617  ::new( value_ptr() ) value_type( il, std::forward<Args>(args)... );
618  }
619 
620 #endif
621 
623  {
624  value_ptr()->~T();
625  }
626 
627  value_type const * value_ptr() const
628  {
629  return as<value_type>();
630  }
631 
633  {
634  return as<value_type>();
635  }
636 
638  {
639  return * value_ptr();
640  }
641 
643  {
644  return * value_ptr();
645  }
646 
647 #if optional_CPP11_OR_GREATER
648 
649  value_type const && value() const optional_refref_qual
650  {
651  return std::move( value() );
652  }
653 
655  {
656  return std::move( value() );
657  }
658 
659 #endif
660 
661 #if optional_CPP11_OR_GREATER
662 
663  using aligned_storage_t = typename std::aligned_storage< sizeof(value_type), alignof(value_type) >::type;
664  aligned_storage_t data;
665 
666 #elif optional_CONFIG_MAX_ALIGN_HACK
667 
668  typedef struct { unsigned char data[ sizeof(value_type) ]; } aligned_storage_t;
669 
670  max_align_t hack;
671  aligned_storage_t data;
672 
673 #else
674  typedef optional_ALIGN_AS(value_type) align_as_type;
675 
676  typedef struct { align_as_type data[ 1 + ( sizeof(value_type) - 1 ) / sizeof(align_as_type) ]; } aligned_storage_t;
677  aligned_storage_t data;
678 
679 # undef optional_ALIGN_AS
680 
681 #endif // optional_CONFIG_MAX_ALIGN_HACK
682 
684  {
685  return &data;
686  }
687 
688  void const * ptr() const optional_noexcept
689  {
690  return &data;
691  }
692 
693  template <typename U>
694  U * as()
695  {
696  return reinterpret_cast<U*>( ptr() );
697  }
698 
699  template <typename U>
700  U const * as() const
701  {
702  return reinterpret_cast<U const *>( ptr() );
703  }
704 };
705 
706 } // namespace detail
707 
709 
710 struct nullopt_t
711 {
712  struct init{};
714 };
715 
716 #if optional_HAVE( CONSTEXPR_11 )
717 constexpr nullopt_t nullopt{ nullopt_t::init{} };
718 #else
719 // extra parenthesis to prevent the most vexing parse:
720 const nullopt_t nullopt(( nullopt_t::init() ));
721 #endif
722 
724 
725 class bad_optional_access : public std::logic_error
726 {
727 public:
729  : logic_error( "bad optional access" ) {}
730 };
731 
733 
734 template< typename T>
735 class optional
736 {
737 private:
738  template< typename > friend class optional;
739 
740  typedef void (optional::*safe_bool)() const;
741 
742 public:
743  typedef T value_type;
744 
745  // x.x.3.1, constructors
746 
747  // 1a - default construct
749  : has_value_( false )
750  , contained()
751  {}
752 
753  // 1b - construct explicitly empty
755  : has_value_( false )
756  , contained()
757  {}
758 
759  // 2 - copy-construct
762  optional_REQUIRES_A(
763  true || std::is_copy_constructible<T>::value
764  )
765 #endif
766  )
767  : has_value_( other.has_value() )
768  {
769  if ( other.has_value() )
770  contained.construct_value( other.contained.value() );
771  }
772 
773 #if optional_CPP11_OR_GREATER
774 
775  // 3 (C++11) - move-construct from optional
777  optional_REQUIRES_A(
778  true || std::is_move_constructible<T>::value
779  )
780  ) noexcept( std::is_nothrow_move_constructible<T>::value )
781  : has_value_( other.has_value() )
782  {
783  if ( other.has_value() )
784  contained.construct_value( std::move( other.contained.value() ) );
785  }
786 
787  // 4 (C++11) - explicit converting copy-construct from optional
788  template< typename U >
789  explicit optional( optional<U> const & other
790  optional_REQUIRES_A(
791  std::is_constructible<T, U const &>::value
792  && !std::is_constructible<T, optional<U> & >::value
793  && !std::is_constructible<T, optional<U> && >::value
794  && !std::is_constructible<T, optional<U> const & >::value
795  && !std::is_constructible<T, optional<U> const && >::value
796  && !std::is_convertible< optional<U> & , T>::value
797  && !std::is_convertible< optional<U> && , T>::value
798  && !std::is_convertible< optional<U> const & , T>::value
799  && !std::is_convertible< optional<U> const &&, T>::value
800  && !std::is_convertible< U const & , T>::value /*=> explicit */
801  )
802  )
803  : has_value_( other.has_value() )
804  {
805  if ( other.has_value() )
806  contained.construct_value( other.contained.value() );
807  }
808 #endif // optional_CPP11_OR_GREATER
809 
810  // 4 (C++98 and later) - non-explicit converting copy-construct from optional
811  template< typename U >
812  optional( optional<U> const & other
814  optional_REQUIRES_A(
815  std::is_constructible<T, U const &>::value
816  && !std::is_constructible<T, optional<U> & >::value
817  && !std::is_constructible<T, optional<U> && >::value
818  && !std::is_constructible<T, optional<U> const & >::value
819  && !std::is_constructible<T, optional<U> const && >::value
820  && !std::is_convertible< optional<U> & , T>::value
821  && !std::is_convertible< optional<U> && , T>::value
822  && !std::is_convertible< optional<U> const & , T>::value
823  && !std::is_convertible< optional<U> const &&, T>::value
824  && std::is_convertible< U const & , T>::value /*=> non-explicit */
825  )
826 #endif // optional_CPP11_OR_GREATER
827  )
828  : has_value_( other.has_value() )
829  {
830  if ( other.has_value() )
831  contained.construct_value( other.contained.value() );
832  }
833 
834 #if optional_CPP11_OR_GREATER
835 
836  // 5a (C++11) - explicit converting move-construct from optional
837  template< typename U >
838  optional( optional<U> && other
839  optional_REQUIRES_A(
840  std::is_constructible<T, U const &>::value
841  && !std::is_constructible<T, optional<U> & >::value
842  && !std::is_constructible<T, optional<U> && >::value
843  && !std::is_constructible<T, optional<U> const & >::value
844  && !std::is_constructible<T, optional<U> const && >::value
845  && !std::is_convertible< optional<U> & , T>::value
846  && !std::is_convertible< optional<U> && , T>::value
847  && !std::is_convertible< optional<U> const & , T>::value
848  && !std::is_convertible< optional<U> const &&, T>::value
849  && !std::is_convertible< U &&, T>::value /*=> explicit */
850  )
851  )
852  : has_value_( other.has_value() )
853  {
854  if ( other.has_value() )
855  contained.construct_value( std::move( other.contained.value() ) );
856  }
857 
858  // 5a (C++11) - non-explicit converting move-construct from optional
859  template< typename U >
860  optional( optional<U> && other
861  optional_REQUIRES_A(
862  std::is_constructible<T, U const &>::value
863  && !std::is_constructible<T, optional<U> & >::value
864  && !std::is_constructible<T, optional<U> && >::value
865  && !std::is_constructible<T, optional<U> const & >::value
866  && !std::is_constructible<T, optional<U> const && >::value
867  && !std::is_convertible< optional<U> & , T>::value
868  && !std::is_convertible< optional<U> && , T>::value
869  && !std::is_convertible< optional<U> const & , T>::value
870  && !std::is_convertible< optional<U> const &&, T>::value
871  && std::is_convertible< U &&, T>::value /*=> non-explicit */
872  )
873  )
874  : has_value_( other.has_value() )
875  {
876  if ( other.has_value() )
877  contained.construct_value( std::move( other.contained.value() ) );
878  }
879 
880  // 6 (C++11) - in-place construct
881  template< typename... Args
882  optional_REQUIRES_T(
883  std::is_constructible<T, Args&&...>::value
884  )
885  >
886  optional_constexpr explicit optional( nonstd_lite_in_place_t(T), Args&&... args )
887  : has_value_( true )
888  , contained( T( std::forward<Args>(args)...) )
889  {}
890 
891  // 7 (C++11) - in-place construct, initializer-list
892  template< typename U, typename... Args
893  optional_REQUIRES_T(
894  std::is_constructible<T, std::initializer_list<U>&, Args&&...>::value
895  )
896  >
897  optional_constexpr explicit optional( nonstd_lite_in_place_t(T), std::initializer_list<U> il, Args&&... args )
898  : has_value_( true )
899  , contained( T( il, std::forward<Args>(args)...) )
900  {}
901 
902  // 8a (C++11) - explicit move construct from value
903  template< typename U = value_type >
904  optional_constexpr explicit optional( U && value
905  optional_REQUIRES_A(
906  std::is_constructible<T, U&&>::value
907  && !std::is_same<typename std20::remove_cvref<U>::type, nonstd_lite_in_place_t(U)>::value
908  && !std::is_same<typename std20::remove_cvref<U>::type, optional<T>>::value
909  && !std::is_convertible<U&&, T>::value /*=> explicit */
910  )
911  )
912  : has_value_( true )
913  , contained( std::forward<U>( value ) )
914  {}
915 
916  // 8a (C++11) - non-explicit move construct from value
917  template< typename U = value_type >
918  optional_constexpr optional( U && value
919  optional_REQUIRES_A(
920  std::is_constructible<T, U&&>::value
921  && !std::is_same<typename std20::remove_cvref<U>::type, nonstd_lite_in_place_t(U)>::value
922  && !std::is_same<typename std20::remove_cvref<U>::type, optional<T>>::value
923  && std::is_convertible<U&&, T>::value /*=> non-explicit */
924  )
925  )
926  : has_value_( true )
927  , contained( std::forward<U>( value ) )
928  {}
929 
930 #else // optional_CPP11_OR_GREATER
931 
932  // 8 (C++98)
934  : has_value_( true )
935  , contained( value )
936  {}
937 
938 #endif // optional_CPP11_OR_GREATER
939 
940  // x.x.3.2, destructor
941 
943  {
944  if ( has_value() )
945  contained.destruct_value();
946  }
947 
948  // x.x.3.3, assignment
949 
950  // 1 (C++98and later) - assign explicitly empty
952  {
953  reset();
954  return *this;
955  }
956 
957  // 2 (C++98and later) - copy-assign from optional
958 #if optional_CPP11_OR_GREATER
959  optional_REQUIRES_R(
960  optional &,
961  true
962 // std::is_copy_constructible<T>::value
963 // && std::is_copy_assignable<T>::value
964  )
965  operator=( optional const & other )
966  noexcept(
967  std::is_nothrow_move_assignable<T>::value
968  && std::is_nothrow_move_constructible<T>::value
969  )
970 #else
971  optional & operator=( optional const & other )
972 #endif
973  {
974  if ( has_value() == true && other.has_value() == false ) reset();
975  else if ( has_value() == false && other.has_value() == true ) initialize( *other );
976  else if ( has_value() == true && other.has_value() == true ) contained.value() = *other;
977  return *this;
978  }
979 
980 #if optional_CPP11_OR_GREATER
981 
982  // 3 (C++11) - move-assign from optional
983  optional_REQUIRES_R(
984  optional &,
985  true
986 // std::is_move_constructible<T>::value
987 // && std::is_move_assignable<T>::value
988  )
989  operator=( optional && other ) noexcept
990  {
991  if ( has_value() == true && other.has_value() == false ) reset();
992  else if ( has_value() == false && other.has_value() == true ) initialize( std::move( *other ) );
993  else if ( has_value() == true && other.has_value() == true ) contained.value() = std::move( *other );
994  return *this;
995  }
996 
997  // 4 (C++11) - move-assign from value
998  template< typename U = T >
999  optional_REQUIRES_R(
1000  optional &,
1001  std::is_constructible<T , U>::value
1002  && std::is_assignable<T&, U>::value
1003  && !std::is_same<typename std20::remove_cvref<U>::type, nonstd_lite_in_place_t(U)>::value
1004  && !std::is_same<typename std20::remove_cvref<U>::type, optional<T>>::value
1005 // && !(std::is_scalar<T>::value && std::is_same<T, typename std::decay<U>::type>::value)
1006  )
1007  operator=( U && value )
1008  {
1009  if ( has_value() ) contained.value() = std::forward<U>( value );
1010  else initialize( T( std::forward<U>( value ) ) );
1011  return *this;
1012  }
1013 
1014 #else // optional_CPP11_OR_GREATER
1015 
1016  // 4 (C++98) - copy-assign from value
1017  template< typename U /*= T*/ >
1018  optional & operator=( U const & value )
1019  {
1020  if ( has_value() ) contained.value() = value;
1021  else initialize( T( value ) );
1022  return *this;
1023  }
1024 
1025 #endif // optional_CPP11_OR_GREATER
1026 
1027  // 5 (C++98 and later) - converting copy-assign from optional
1028  template< typename U >
1029 #if optional_CPP11_OR_GREATER
1030  optional_REQUIRES_R(
1031  optional&,
1032  std::is_constructible< T , U const &>::value
1033  && std::is_assignable< T&, U const &>::value
1034  && !std::is_constructible<T, optional<U> & >::value
1035  && !std::is_constructible<T, optional<U> && >::value
1036  && !std::is_constructible<T, optional<U> const & >::value
1037  && !std::is_constructible<T, optional<U> const && >::value
1038  && !std::is_convertible< optional<U> & , T>::value
1039  && !std::is_convertible< optional<U> && , T>::value
1040  && !std::is_convertible< optional<U> const & , T>::value
1041  && !std::is_convertible< optional<U> const &&, T>::value
1042  && !std::is_assignable< T&, optional<U> & >::value
1043  && !std::is_assignable< T&, optional<U> && >::value
1044  && !std::is_assignable< T&, optional<U> const & >::value
1045  && !std::is_assignable< T&, optional<U> const && >::value
1046  )
1047 #else
1048  optional&
1049 #endif // optional_CPP11_OR_GREATER
1050  operator=( optional<U> const & other )
1051  {
1052  return *this = optional( other );
1053  }
1054 
1055 #if optional_CPP11_OR_GREATER
1056 
1057  // 6 (C++11) - converting move-assign from optional
1058  template< typename U >
1059  optional_REQUIRES_R(
1060  optional&,
1061  std::is_constructible< T , U>::value
1062  && std::is_assignable< T&, U>::value
1063  && !std::is_constructible<T, optional<U> & >::value
1064  && !std::is_constructible<T, optional<U> && >::value
1065  && !std::is_constructible<T, optional<U> const & >::value
1066  && !std::is_constructible<T, optional<U> const && >::value
1067  && !std::is_convertible< optional<U> & , T>::value
1068  && !std::is_convertible< optional<U> && , T>::value
1069  && !std::is_convertible< optional<U> const & , T>::value
1070  && !std::is_convertible< optional<U> const &&, T>::value
1071  && !std::is_assignable< T&, optional<U> & >::value
1072  && !std::is_assignable< T&, optional<U> && >::value
1073  && !std::is_assignable< T&, optional<U> const & >::value
1074  && !std::is_assignable< T&, optional<U> const && >::value
1075  )
1076  operator=( optional<U> && other )
1077  {
1078  return *this = optional( std::move( other ) );
1079  }
1080 
1081  // 7 (C++11) - emplace
1082  template< typename... Args
1083  optional_REQUIRES_T(
1084  std::is_constructible<T, Args&&...>::value
1085  )
1086  >
1087  T& emplace( Args&&... args )
1088  {
1089  *this = nullopt;
1090  contained.emplace( std::forward<Args>(args)... );
1091  has_value_ = true;
1092  return contained.value();
1093  }
1094 
1095  // 8 (C++11) - emplace, initializer-list
1096  template< typename U, typename... Args
1097  optional_REQUIRES_T(
1098  std::is_constructible<T, std::initializer_list<U>&, Args&&...>::value
1099  )
1100  >
1101  T& emplace( std::initializer_list<U> il, Args&&... args )
1102  {
1103  *this = nullopt;
1104  contained.emplace( il, std::forward<Args>(args)... );
1105  has_value_ = true;
1106  return contained.value();
1107  }
1108 
1109 #endif // optional_CPP11_OR_GREATER
1110 
1111  // x.x.3.4, swap
1112 
1113  void swap( optional & other )
1114 #if optional_CPP11_OR_GREATER
1115  noexcept(
1116  std::is_nothrow_move_constructible<T>::value
1117  && noexcept( std::swap( std::declval<T&>(), std::declval<T&>() ) )
1118  )
1119 #endif
1120  {
1121  using std::swap;
1122  if ( has_value() == true && other.has_value() == true ) { swap( **this, *other ); }
1123  else if ( has_value() == false && other.has_value() == true ) { initialize( *other ); other.reset(); }
1124  else if ( has_value() == true && other.has_value() == false ) { other.initialize( **this ); reset(); }
1125  }
1126 
1127  // x.x.3.5, observers
1128 
1130  {
1131  return assert( has_value() ),
1132  contained.value_ptr();
1133  }
1134 
1136  {
1137  return assert( has_value() ),
1138  contained.value_ptr();
1139  }
1140 
1142  {
1143  return assert( has_value() ),
1144  contained.value();
1145  }
1146 
1148  {
1149  return assert( has_value() ),
1150  contained.value();
1151  }
1152 
1153 #if optional_CPP11_OR_GREATER
1154 
1155  optional_constexpr value_type const && operator *() const optional_refref_qual
1156  {
1157  return std::move( **this );
1158  }
1159 
1161  {
1162  return std::move( **this );
1163  }
1164 
1165 #endif
1166 
1167 #if optional_CPP11_OR_GREATER
1168  optional_constexpr explicit operator bool() const optional_noexcept
1169  {
1170  return has_value();
1171  }
1172 #else
1173  optional_constexpr operator safe_bool() const optional_noexcept
1174  {
1175  return has_value() ? &optional::this_type_does_not_support_comparisons : 0;
1176  }
1177 #endif
1178 
1180  {
1181  return has_value_;
1182  }
1183 
1185  {
1186  if ( ! has_value() )
1187  throw bad_optional_access();
1188 
1189  return contained.value();
1190  }
1191 
1193  {
1194  if ( ! has_value() )
1195  throw bad_optional_access();
1196 
1197  return contained.value();
1198  }
1199 
1200 #if optional_HAVE( REF_QUALIFIER )
1201 
1203  {
1204  return std::move( value() );
1205  }
1206 
1208  {
1209  return std::move( value() );
1210  }
1211 
1212 #endif
1213 
1214 #if optional_CPP11_OR_GREATER
1215 
1216  template< typename U >
1217  optional_constexpr value_type value_or( U && v ) const optional_ref_qual
1218  {
1219  return has_value() ? contained.value() : static_cast<T>(std::forward<U>( v ) );
1220  }
1221 
1222  template< typename U >
1224  {
1225  return has_value() ? std::move( contained.value() ) : static_cast<T>(std::forward<U>( v ) );
1226  }
1227 
1228 #else
1229 
1230  template< typename U >
1232  {
1233  return has_value() ? contained.value() : static_cast<value_type>( v );
1234  }
1235 
1236 #endif // optional_CPP11_OR_GREATER
1237 
1238  // x.x.3.6, modifiers
1239 
1241  {
1242  if ( has_value() )
1243  contained.destruct_value();
1244 
1245  has_value_ = false;
1246  }
1247 
1248 private:
1249  void this_type_does_not_support_comparisons() const {}
1250 
1251  template< typename V >
1252  void initialize( V const & value )
1253  {
1254  assert( ! has_value() );
1255  contained.construct_value( value );
1256  has_value_ = true;
1257  }
1258 
1259 #if optional_CPP11_OR_GREATER
1260  template< typename V >
1261  void initialize( V && value )
1262  {
1263  assert( ! has_value() );
1264  contained.construct_value( std::move( value ) );
1265  has_value_ = true;
1266  }
1267 
1268 #endif
1269 
1270 private:
1271  bool has_value_;
1272  detail::storage_t< value_type > contained;
1273 
1274 };
1275 
1276 // Relational operators
1277 
1278 template< typename T, typename U >
1279 inline optional_constexpr bool operator==( optional<T> const & x, optional<U> const & y )
1280 {
1281  return bool(x) != bool(y) ? false : !bool( x ) ? true : *x == *y;
1282 }
1283 
1284 template< typename T, typename U >
1285 inline optional_constexpr bool operator!=( optional<T> const & x, optional<U> const & y )
1286 {
1287  return !(x == y);
1288 }
1289 
1290 template< typename T, typename U >
1291 inline optional_constexpr bool operator<( optional<T> const & x, optional<U> const & y )
1292 {
1293  return (!y) ? false : (!x) ? true : *x < *y;
1294 }
1295 
1296 template< typename T, typename U >
1297 inline optional_constexpr bool operator>( optional<T> const & x, optional<U> const & y )
1298 {
1299  return (y < x);
1300 }
1301 
1302 template< typename T, typename U >
1303 inline optional_constexpr bool operator<=( optional<T> const & x, optional<U> const & y )
1304 {
1305  return !(y < x);
1306 }
1307 
1308 template< typename T, typename U >
1309 inline optional_constexpr bool operator>=( optional<T> const & x, optional<U> const & y )
1310 {
1311  return !(x < y);
1312 }
1313 
1314 // Comparison with nullopt
1315 
1316 template< typename T >
1318 {
1319  return (!x);
1320 }
1321 
1322 template< typename T >
1324 {
1325  return (!x);
1326 }
1327 
1328 template< typename T >
1330 {
1331  return bool(x);
1332 }
1333 
1334 template< typename T >
1336 {
1337  return bool(x);
1338 }
1339 
1340 template< typename T >
1342 {
1343  return false;
1344 }
1345 
1346 template< typename T >
1348 {
1349  return bool(x);
1350 }
1351 
1352 template< typename T >
1354 {
1355  return (!x);
1356 }
1357 
1358 template< typename T >
1360 {
1361  return true;
1362 }
1363 
1364 template< typename T >
1366 {
1367  return bool(x);
1368 }
1369 
1370 template< typename T >
1372 {
1373  return false;
1374 }
1375 
1376 template< typename T >
1378 {
1379  return true;
1380 }
1381 
1382 template< typename T >
1384 {
1385  return (!x);
1386 }
1387 
1388 // Comparison with T
1389 
1390 template< typename T, typename U >
1391 inline optional_constexpr bool operator==( optional<T> const & x, U const & v )
1392 {
1393  return bool(x) ? *x == v : false;
1394 }
1395 
1396 template< typename T, typename U >
1397 inline optional_constexpr bool operator==( U const & v, optional<T> const & x )
1398 {
1399  return bool(x) ? v == *x : false;
1400 }
1401 
1402 template< typename T, typename U >
1403 inline optional_constexpr bool operator!=( optional<T> const & x, U const & v )
1404 {
1405  return bool(x) ? *x != v : true;
1406 }
1407 
1408 template< typename T, typename U >
1409 inline optional_constexpr bool operator!=( U const & v, optional<T> const & x )
1410 {
1411  return bool(x) ? v != *x : true;
1412 }
1413 
1414 template< typename T, typename U >
1415 inline optional_constexpr bool operator<( optional<T> const & x, U const & v )
1416 {
1417  return bool(x) ? *x < v : true;
1418 }
1419 
1420 template< typename T, typename U >
1421 inline optional_constexpr bool operator<( U const & v, optional<T> const & x )
1422 {
1423  return bool(x) ? v < *x : false;
1424 }
1425 
1426 template< typename T, typename U >
1427 inline optional_constexpr bool operator<=( optional<T> const & x, U const & v )
1428 {
1429  return bool(x) ? *x <= v : true;
1430 }
1431 
1432 template< typename T, typename U >
1433 inline optional_constexpr bool operator<=( U const & v, optional<T> const & x )
1434 {
1435  return bool(x) ? v <= *x : false;
1436 }
1437 
1438 template< typename T, typename U >
1439 inline optional_constexpr bool operator>( optional<T> const & x, U const & v )
1440 {
1441  return bool(x) ? *x > v : false;
1442 }
1443 
1444 template< typename T, typename U >
1445 inline optional_constexpr bool operator>( U const & v, optional<T> const & x )
1446 {
1447  return bool(x) ? v > *x : true;
1448 }
1449 
1450 template< typename T, typename U >
1451 inline optional_constexpr bool operator>=( optional<T> const & x, U const & v )
1452 {
1453  return bool(x) ? *x >= v : false;
1454 }
1455 
1456 template< typename T, typename U >
1457 inline optional_constexpr bool operator>=( U const & v, optional<T> const & x )
1458 {
1459  return bool(x) ? v >= *x : true;
1460 }
1461 
1462 // Specialized algorithms
1463 
1464 template< typename T >
1465 void swap( optional<T> & x, optional<T> & y )
1466 #if optional_CPP11_OR_GREATER
1467  noexcept( noexcept( x.swap(y) ) )
1468 #endif
1469 {
1470  x.swap( y );
1471 }
1472 
1473 #if optional_CPP11_OR_GREATER
1474 
1475 template< typename T >
1477 {
1478  return optional< typename std::decay<T>::type >( std::forward<T>( value ) );
1479 }
1480 
1481 template< typename T, typename...Args >
1482 optional_constexpr optional<T> make_optional( Args&&... args )
1483 {
1484  return optional<T>( nonstd_lite_in_place(T), std::forward<Args>(args)...);
1485 }
1486 
1487 template< typename T, typename U, typename... Args >
1488 optional_constexpr optional<T> make_optional( std::initializer_list<U> il, Args&&... args )
1489 {
1490  return optional<T>( nonstd_lite_in_place(T), il, std::forward<Args>(args)...);
1491 }
1492 
1493 #else
1494 
1495 template< typename T >
1497 {
1498  return optional<T>( value );
1499 }
1500 
1501 #endif // optional_CPP11_OR_GREATER
1502 
1503 } // namespace optional_lite
1504 
1505 using namespace optional_lite;
1506 
1507 } // namespace nonstd
1508 
1509 #if optional_CPP11_OR_GREATER
1510 
1511 // specialize the std::hash algorithm:
1512 
1513 namespace std {
1514 
1515 template< class T >
1516 struct hash< nonstd::optional<T> >
1517 {
1518 public:
1519  std::size_t operator()( nonstd::optional<T> const & v ) const optional_noexcept
1520  {
1521  return bool( v ) ? hash<T>()( *v ) : 0;
1522  }
1523 };
1524 
1525 } //namespace std
1526 
1527 #endif // optional_CPP11_OR_GREATER
1528 
1529 #if defined(__clang__)
1530 # pragma clang diagnostic pop
1531 #elif defined(__GNUC__)
1532 # pragma GCC diagnostic pop
1533 #endif
1534 
1535 #endif // optional_USES_STD_OPTIONAL
1536 
1537 #endif // NONSTD_OPTIONAL_LITE_HPP
conditional< N==sizeof(typename List::head), typename List::head, typename type_of_size< typename List::tail, N >::type >::type type
Definition: optional.hpp:526
#define nonstd_lite_in_place_t( T)
Definition: optional.hpp:144
#define optional_noexcept
Definition: optional.hpp:330
#define optional_ref_qual
Definition: optional.hpp:343
value_type const * value_ptr() const
Definition: optional.hpp:627
optional_constexpr bool operator==(optional< T > const &x, optional< U > const &y)
Definition: optional.hpp:1279
void swap(optional< T > &x, optional< T > &y)
Definition: optional.hpp:1465
optional_constexpr14 value_type & value() optional_ref_qual
Definition: optional.hpp:1192
optional_constexpr14 value_type & operator *() optional_ref_qual
Definition: optional.hpp:1147
typedef optional_ALIGN_AS(value_type) align_as_type
optional< T > make_optional(T const &value)
Definition: optional.hpp:1496
optional_constexpr14 value_type const & value() const optional_ref_qual
Definition: optional.hpp:1184
void reset() optional_noexcept
Definition: optional.hpp:1240
optional_constexpr nullopt_t(init)
Definition: optional.hpp:713
void const * ptr() const optional_noexcept
Definition: optional.hpp:688
optional & operator=(nullopt_t) optional_noexcept
Definition: optional.hpp:951
in_place_t in_place_index(detail::in_place_index_tag< K >=detail::in_place_index_tag< K >())
Definition: any.hpp:132
optional(value_type const &value)
Definition: optional.hpp:933
void construct_value(value_type const &v)
Definition: optional.hpp:591
optional & operator=(U const &value)
Definition: optional.hpp:1018
std::size_t hash(T const &v)
Definition: variant.hpp:807
optional & operator=(optional< U > const &other)
Definition: optional.hpp:1050
optional_constexpr bool operator<=(optional< T > const &x, optional< U > const &y)
Definition: optional.hpp:1303
optional_constexpr14 value_type * operator ->()
Definition: optional.hpp:1135
disengaged state tag
Definition: optional.hpp:710
#define optional_CONFIG_ALIGN_AS_FALLBACK
Definition: optional.hpp:201
optional_constexpr value_type const & operator *() const optional_ref_qual
Definition: optional.hpp:1141
value_type & value() optional_ref_qual
Definition: optional.hpp:642
optional_constexpr14 optional(optional const &other)
Definition: optional.hpp:760
optional_constexpr bool operator>(optional< T > const &x, optional< U > const &y)
Definition: optional.hpp:1297
#define optional_refref_qual
Definition: optional.hpp:344
optional_constexpr bool operator<(optional< T > const &x, optional< U > const &y)
Definition: optional.hpp:1291
Definition: any.hpp:100
optional_constexpr bool operator!=(optional< T > const &x, optional< U > const &y)
Definition: optional.hpp:1285
optional_constexpr value_type value_or(U const &v) const
Definition: optional.hpp:1231
value_type const & value() const optional_ref_qual
Definition: optional.hpp:637
#define optional_CPP11_OR_GREATER
Definition: optional.hpp:45
void * ptr() optional_noexcept
Definition: optional.hpp:683
void swap(optional &other)
Definition: optional.hpp:1113
optional_constexpr optional(nullopt_t) optional_noexcept
Definition: optional.hpp:754
optional_constexpr optional() optional_noexcept
Definition: optional.hpp:748
optional(optional< U > const &other)
Definition: optional.hpp:812
#define optional_constexpr14
Definition: optional.hpp:324
optional & operator=(optional const &other)
Definition: optional.hpp:971
#define nonstd_lite_in_place( T)
Definition: optional.hpp:148
in_place_t in_place_type(detail::in_place_type_tag< T >=detail::in_place_type_tag< T >())
Definition: any.hpp:126
C++03 constructed union to hold value.
Definition: optional.hpp:577
optional_constexpr bool operator>=(optional< T > const &x, optional< U > const &y)
Definition: optional.hpp:1309
optional_constexpr value_type const * operator ->() const
Definition: optional.hpp:1129
const nullopt_t nullopt((nullopt_t::init()))
#define optional_constexpr
Definition: optional.hpp:318
in_place_t in_place(detail::in_place_type_tag< T >=detail::in_place_type_tag< T >())
Definition: any.hpp:114
optional_constexpr bool has_value() const optional_noexcept
Definition: optional.hpp:1179