mirror of
https://github.com/boostorg/optional.git
synced 2025-07-16 05:42:07 +02:00
Reorganized docs. Minor code fix wrt opt refs
This commit is contained in:
@ -45,14 +45,13 @@ Distributed under the Boost Software License, Version 1.0.
|
|||||||
[def __GO_TO__ [$images/callouts/R.png]]
|
[def __GO_TO__ [$images/callouts/R.png]]
|
||||||
|
|
||||||
|
|
||||||
[section Introduction]
|
[heading Introduction]
|
||||||
Class template `optional` is a wrapper for representing 'optional' (or 'nullable') objects who may not (yet) contain a valid value. Optional objects offer full value semantics; they are good for passing by value and usage inside STL containers. This is a header-only library.
|
Class template `optional` is a wrapper for representing 'optional' (or 'nullable') objects who may not (yet) contain a valid value. Optional objects offer full value semantics; they are good for passing by value and usage inside STL containers. This is a header-only library.
|
||||||
|
|
||||||
[section Problem]
|
[heading Problem]
|
||||||
Suppose we want to read a parameter form a config file which represents some integral value, let's call it `"MaxValue"`. It is possible that this parameter is not specified; such situation is no error. It is valid to not specify the parameter and in that case the program is supposed to behave slightly different. Also suppose that any possible value of type `int` is a valid value for `"MaxValue"`, so we cannot jut use `-1` to represent the absence of the parameter in the config file.
|
Suppose we want to read a parameter form a config file which represents some integral value, let's call it `"MaxValue"`. It is possible that this parameter is not specified; such situation is no error. It is valid to not specify the parameter and in that case the program is supposed to behave slightly different. Also suppose that any possible value of type `int` is a valid value for `"MaxValue"`, so we cannot jut use `-1` to represent the absence of the parameter in the config file.
|
||||||
[endsect]
|
|
||||||
|
|
||||||
[section Solution]
|
[heading Solution]
|
||||||
|
|
||||||
This is how you solve it with `boost::optional`:
|
This is how you solve it with `boost::optional`:
|
||||||
|
|
||||||
@ -68,16 +67,21 @@ This is how you solve it with `boost::optional`:
|
|||||||
runWithNoMax();
|
runWithNoMax();
|
||||||
}
|
}
|
||||||
|
|
||||||
[endsect]
|
|
||||||
[endsect]
|
|
||||||
|
|
||||||
[include 01_tutorial.qbk]
|
|
||||||
[include 02_discussion.qbk]
|
[include 01_quick_start.qbk]
|
||||||
[include 03_development.qbk]
|
[section Tutorial]
|
||||||
[include 04_reference.qbk]
|
[include 12_motivation.qbk]
|
||||||
[include 05_examples.qbk]
|
[include 13_development.qbk]
|
||||||
[include 10_optional_references.qbk]
|
[include 14_optional_references.qbk]
|
||||||
[include 11_special_cases.qbk]
|
[include 15_in_place_factories.qbk]
|
||||||
|
[include 16_optional_bool.qbk]
|
||||||
|
[include 17_exception_safety.qbk]
|
||||||
|
[include 18_type_requirements.qbk]
|
||||||
|
[endsect]
|
||||||
|
[section Reference]
|
||||||
|
[include 20_reference.qbk]
|
||||||
|
[endsect]
|
||||||
[include 90_dependencies.qbk]
|
[include 90_dependencies.qbk]
|
||||||
[include 91_acknowledgments.qbk]
|
[include 91_acknowledgments.qbk]
|
||||||
|
|
||||||
|
@ -10,9 +10,9 @@
|
|||||||
]
|
]
|
||||||
|
|
||||||
|
|
||||||
[section Tutorial]
|
[section Quick Start]
|
||||||
|
|
||||||
[section Optional return values]
|
[heading Optional return values]
|
||||||
|
|
||||||
Let's write and use a converter function that converts an a `std::string` to an `int`. It is possible that for a given string (e.g. `"cat"`) there exist no value of type `int` capable of representing the conversion result. We do not consider such situation an error. We expect that the converter can be used only to check if the conversion is possible. A natural signature for this function can be:
|
Let's write and use a converter function that converts an a `std::string` to an `int`. It is possible that for a given string (e.g. `"cat"`) there exist no value of type `int` capable of representing the conversion result. We do not consider such situation an error. We expect that the converter can be used only to check if the conversion is possible. A natural signature for this function can be:
|
||||||
|
|
||||||
@ -62,10 +62,28 @@ This uses the `atoi`-like approach to conversions: if `text` does not represent
|
|||||||
|
|
||||||
Observe the two return statements. `return i` uses the converting constructor that can create `optional<T>` from `T`. Thus constructed optional object is initialized and its value is a copy of `i`. The other return statement uses another converting constructor from a special tag `boost::none`. It is used to indicate that we want to create an uninitialized optional object.
|
Observe the two return statements. `return i` uses the converting constructor that can create `optional<T>` from `T`. Thus constructed optional object is initialized and its value is a copy of `i`. The other return statement uses another converting constructor from a special tag `boost::none`. It is used to indicate that we want to create an uninitialized optional object.
|
||||||
|
|
||||||
|
[/endsect]
|
||||||
|
|
||||||
[endsect]
|
[heading Optional automatic variables]
|
||||||
|
|
||||||
|
We could write function `convert` in a slightly different manner, so that it has a single `return`-statement:
|
||||||
|
|
||||||
|
boost::optionl<int> convert(const std::string& text)
|
||||||
|
{
|
||||||
|
boost::optionl<int> ans;
|
||||||
|
std::stringstream s(text);
|
||||||
|
int i;
|
||||||
|
if ((s >> i) && s.get() == std::char_traits<char>::eof())
|
||||||
|
ans = i;
|
||||||
|
|
||||||
|
return ans;
|
||||||
|
}
|
||||||
|
|
||||||
|
The default constructor of `optional` creates an unitialized optional object. Unlike with `int`s you cannot have an `optional<int>` in an indeterminate state. Its state is always well defined. Instruction `ans = i` initializes the optional object. It uses the assignment from `int`. In general, for `optional<T>`, when an assignment from `T` is invoked, it can do two things. If the optional object is not initialized our case here), it initializes it with `T`'s copy constructor. If the optional object is already initialized, it assigns the new value to it using `T`'s copy assignment.
|
||||||
|
[/endsect]
|
||||||
|
|
||||||
|
[heading Optional data members]
|
||||||
|
|
||||||
[section Optional data members]
|
|
||||||
Suppose we want to implement a ['lazy load] optimization. This is because we do not want to perform an expensive initialization of our `Resource` until (if at all) it is really used. We can do it this way:
|
Suppose we want to implement a ['lazy load] optimization. This is because we do not want to perform an expensive initialization of our `Resource` until (if at all) it is really used. We can do it this way:
|
||||||
|
|
||||||
class Widget
|
class Widget
|
||||||
@ -86,11 +104,12 @@ Suppose we want to implement a ['lazy load] optimization. This is because we do
|
|||||||
|
|
||||||
`optional`'s default constructor creates an uninitialized optional. No call to `Resource`'s default constructor is attempted. `Resource` doesn't have to be __SGI_DEFAULT_CONSTRUCTIBLE__. In function `getResource` we first check if `resource_` is initialized. This time we do not use the contextual conversion to `bool`, but a comparison with `boost::none`. These two ways are equivalent. Function `emplace` initializes the optional in-place by perfect-forwarding the arguments to the constructor of `Resource`. No copy- or move-construction is involved here. `Resource` doesn't even have to be `MoveConstructible`.
|
`optional`'s default constructor creates an uninitialized optional. No call to `Resource`'s default constructor is attempted. `Resource` doesn't have to be __SGI_DEFAULT_CONSTRUCTIBLE__. In function `getResource` we first check if `resource_` is initialized. This time we do not use the contextual conversion to `bool`, but a comparison with `boost::none`. These two ways are equivalent. Function `emplace` initializes the optional in-place by perfect-forwarding the arguments to the constructor of `Resource`. No copy- or move-construction is involved here. `Resource` doesn't even have to be `MoveConstructible`.
|
||||||
|
|
||||||
[note Function `emplace` is only available on compilers that support rvalue references and variadic templates. If your compiler does not support these features and you still need to avoid any move-constructions, use [link boost_optional.in_place_factories In-Place Factories].]
|
[note Function `emplace` is only available on compilers that support rvalue references and variadic templates. If your compiler does not support these features and you still need to avoid any move-constructions, use [link boost_optional.tutorial.in_place_factories In-Place Factories].]
|
||||||
|
|
||||||
[endsect]
|
[/endsect]
|
||||||
|
|
||||||
|
[heading Bypassing unnecessary default construction]
|
||||||
|
|
||||||
[section Bypassing unnecessary default construction]
|
|
||||||
Suppose we have class `Date`, which does not have a default constructor: there is no good candidate for a default date. We have a function that returns two dates in form of a `boost::tuple`:
|
Suppose we have class `Date`, which does not have a default constructor: there is no good candidate for a default date. We have a function that returns two dates in form of a `boost::tuple`:
|
||||||
|
|
||||||
boost::tuple<Date, Date> getPeriod();
|
boost::tuple<Date, Date> getPeriod();
|
||||||
@ -100,13 +119,13 @@ In other place we want to use the result of `getPeriod`, but want the two dates
|
|||||||
Date begin, end; // Error: no default ctor!
|
Date begin, end; // Error: no default ctor!
|
||||||
boost::tie(begin, end) = getPeriod();
|
boost::tie(begin, end) = getPeriod();
|
||||||
|
|
||||||
The second line works already, this is the capability of Boost.Tuple library, but the first line won't work. We could set some initial invented dates, but it is confusing and may be an unacceptable cost, given that these values will be overwritten in the next line anyway. This is where `optional` can help:
|
The second line works already, this is the capability of Boost.Tuple library, but the first line won't work. We could set some invented initial dates, but it is confusing and may be an unacceptable cost, given that these values will be overwritten in the next line anyway. This is where `optional` can help:
|
||||||
|
|
||||||
boost::optional<Date> begin, end;
|
boost::optional<Date> begin, end;
|
||||||
boost::tie(begin, end) = getPeriod();
|
boost::tie(begin, end) = getPeriod();
|
||||||
|
|
||||||
It works because inside `boost::tie` a move-assignment from `T` is invoked on `optional<T>`, which internally calls a move-constructor of `T`.
|
It works because inside `boost::tie` a move-assignment from `T` is invoked on `optional<T>`, which internally calls a move-constructor of `T`.
|
||||||
[endsect]
|
[/endsect]
|
||||||
|
|
||||||
[endsect]
|
[endsect]
|
||||||
|
|
@ -1,102 +0,0 @@
|
|||||||
[/
|
|
||||||
Boost.Optional
|
|
||||||
|
|
||||||
Copyright (c) 2003-2007 Fernando Luis Cacciola Carballal
|
|
||||||
|
|
||||||
Distributed under the Boost Software License, Version 1.0.
|
|
||||||
(See accompanying file LICENSE_1_0.txt or copy at
|
|
||||||
http://www.boost.org/LICENSE_1_0.txt)
|
|
||||||
]
|
|
||||||
|
|
||||||
|
|
||||||
[section Examples]
|
|
||||||
|
|
||||||
[section Optional return values]
|
|
||||||
|
|
||||||
optional<char> get_async_input()
|
|
||||||
{
|
|
||||||
if ( !queue.empty() )
|
|
||||||
return optional<char>(queue.top());
|
|
||||||
else return optional<char>(); // uninitialized
|
|
||||||
}
|
|
||||||
|
|
||||||
void receive_async_message()
|
|
||||||
{
|
|
||||||
optional<char> rcv ;
|
|
||||||
// The safe boolean conversion from 'rcv' is used here.
|
|
||||||
while ( (rcv = get_async_input()) && !timeout() )
|
|
||||||
output(*rcv);
|
|
||||||
}
|
|
||||||
|
|
||||||
[endsect]
|
|
||||||
|
|
||||||
[section Optional local variables]
|
|
||||||
|
|
||||||
optional<string> name ;
|
|
||||||
if ( database.open() )
|
|
||||||
{
|
|
||||||
name = database.lookup(employer_name) ;
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
if ( can_ask_user )
|
|
||||||
name = user.ask(employer_name) ;
|
|
||||||
}
|
|
||||||
|
|
||||||
if ( name )
|
|
||||||
print(*name);
|
|
||||||
else print("employer's name not found!");
|
|
||||||
|
|
||||||
[endsect]
|
|
||||||
|
|
||||||
[section Optional data members]
|
|
||||||
|
|
||||||
class figure
|
|
||||||
{
|
|
||||||
public:
|
|
||||||
|
|
||||||
figure()
|
|
||||||
{
|
|
||||||
// data member 'm_clipping_rect' is uninitialized at this point.
|
|
||||||
}
|
|
||||||
|
|
||||||
void clip_in_rect ( rect const& rect )
|
|
||||||
{
|
|
||||||
....
|
|
||||||
m_clipping_rect = rect ; // initialized here.
|
|
||||||
}
|
|
||||||
|
|
||||||
void draw ( canvas& cvs )
|
|
||||||
{
|
|
||||||
if ( m_clipping_rect )
|
|
||||||
do_clipping(*m_clipping_rect);
|
|
||||||
|
|
||||||
cvs.drawXXX(..);
|
|
||||||
}
|
|
||||||
|
|
||||||
// this can return NULL.
|
|
||||||
rect const* get_clipping_rect() { return get_pointer(m_clipping_rect); }
|
|
||||||
|
|
||||||
private :
|
|
||||||
|
|
||||||
optional<rect> m_clipping_rect ;
|
|
||||||
|
|
||||||
};
|
|
||||||
|
|
||||||
[endsect]
|
|
||||||
|
|
||||||
[section Bypassing expensive unnecessary default construction]
|
|
||||||
|
|
||||||
class ExpensiveCtor { ... } ;
|
|
||||||
class Fred
|
|
||||||
{
|
|
||||||
Fred() : mLargeVector(10000) {}
|
|
||||||
|
|
||||||
std::vector< optional<ExpensiveCtor> > mLargeVector ;
|
|
||||||
} ;
|
|
||||||
|
|
||||||
[endsect]
|
|
||||||
|
|
||||||
[endsect]
|
|
||||||
|
|
||||||
|
|
@ -1,258 +0,0 @@
|
|||||||
|
|
||||||
[section In-Place Factories]
|
|
||||||
|
|
||||||
One of the typical problems with wrappers and containers is that their
|
|
||||||
interfaces usually provide an operation to initialize or assign the
|
|
||||||
contained object as a copy of some other object. This not only requires the
|
|
||||||
underlying type to be __COPY_CONSTRUCTIBLE__, but also requires the existence of
|
|
||||||
a fully constructed object, often temporary, just to follow the copy from:
|
|
||||||
|
|
||||||
struct X
|
|
||||||
{
|
|
||||||
X ( int, std::string ) ;
|
|
||||||
} ;
|
|
||||||
|
|
||||||
class W
|
|
||||||
{
|
|
||||||
X wrapped_ ;
|
|
||||||
|
|
||||||
public:
|
|
||||||
|
|
||||||
W ( X const& x ) : wrapped_(x) {}
|
|
||||||
} ;
|
|
||||||
|
|
||||||
void foo()
|
|
||||||
{
|
|
||||||
// Temporary object created.
|
|
||||||
W ( X(123,"hello") ) ;
|
|
||||||
}
|
|
||||||
|
|
||||||
A solution to this problem is to support direct construction of the
|
|
||||||
contained object right in the container's storage.
|
|
||||||
In this scheme, the user only needs to supply the arguments to the
|
|
||||||
constructor to use in the wrapped object construction.
|
|
||||||
|
|
||||||
class W
|
|
||||||
{
|
|
||||||
X wrapped_ ;
|
|
||||||
|
|
||||||
public:
|
|
||||||
|
|
||||||
W ( X const& x ) : wrapped_(x) {}
|
|
||||||
W ( int a0, std::string a1) : wrapped_(a0,a1) {}
|
|
||||||
} ;
|
|
||||||
|
|
||||||
void foo()
|
|
||||||
{
|
|
||||||
// Wrapped object constructed in-place
|
|
||||||
// No temporary created.
|
|
||||||
W (123,"hello") ;
|
|
||||||
}
|
|
||||||
|
|
||||||
A limitation of this method is that it doesn't scale well to wrapped
|
|
||||||
objects with multiple constructors nor to generic code were the constructor
|
|
||||||
overloads are unknown.
|
|
||||||
|
|
||||||
The solution presented in this library is the family of [*InPlaceFactories]
|
|
||||||
and [*TypedInPlaceFactories].
|
|
||||||
These factories are a family of classes which encapsulate an increasing
|
|
||||||
number of arbitrary constructor parameters and supply a method to construct
|
|
||||||
an object of a given type using those parameters at an address specified by
|
|
||||||
the user via placement new.
|
|
||||||
|
|
||||||
For example, one member of this family looks like:
|
|
||||||
|
|
||||||
template<class T,class A0, class A1>
|
|
||||||
class TypedInPlaceFactory2
|
|
||||||
{
|
|
||||||
A0 m_a0 ; A1 m_a1 ;
|
|
||||||
|
|
||||||
public:
|
|
||||||
|
|
||||||
TypedInPlaceFactory2( A0 const& a0, A1 const& a1 ) : m_a0(a0), m_a1(a1) {}
|
|
||||||
|
|
||||||
void construct ( void* p ) { new (p) T(m_a0,m_a1) ; }
|
|
||||||
} ;
|
|
||||||
|
|
||||||
A wrapper class aware of this can use it as:
|
|
||||||
|
|
||||||
class W
|
|
||||||
{
|
|
||||||
X wrapped_ ;
|
|
||||||
|
|
||||||
public:
|
|
||||||
|
|
||||||
W ( X const& x ) : wrapped_(x) {}
|
|
||||||
W ( TypedInPlaceFactory2 const& fac ) { fac.construct(&wrapped_) ; }
|
|
||||||
} ;
|
|
||||||
|
|
||||||
void foo()
|
|
||||||
{
|
|
||||||
// Wrapped object constructed in-place via a TypedInPlaceFactory.
|
|
||||||
// No temporary created.
|
|
||||||
W ( TypedInPlaceFactory2<X,int,std::string>(123,"hello")) ;
|
|
||||||
}
|
|
||||||
|
|
||||||
The factories are divided in two groups:
|
|
||||||
|
|
||||||
* [_TypedInPlaceFactories]: those which take the target type as a primary
|
|
||||||
template parameter.
|
|
||||||
* [_InPlaceFactories]: those with a template `construct(void*)` member
|
|
||||||
function taking the target type.
|
|
||||||
|
|
||||||
Within each group, all the family members differ only in the number of
|
|
||||||
parameters allowed.
|
|
||||||
|
|
||||||
This library provides an overloaded set of helper template functions to
|
|
||||||
construct these factories without requiring unnecessary template parameters:
|
|
||||||
|
|
||||||
template<class A0,...,class AN>
|
|
||||||
InPlaceFactoryN <A0,...,AN> in_place ( A0 const& a0, ..., AN const& aN) ;
|
|
||||||
|
|
||||||
template<class T,class A0,...,class AN>
|
|
||||||
TypedInPlaceFactoryN <T,A0,...,AN> in_place ( T const& a0, A0 const& a0, ..., AN const& aN) ;
|
|
||||||
|
|
||||||
In-place factories can be used generically by the wrapper and user as follows:
|
|
||||||
|
|
||||||
class W
|
|
||||||
{
|
|
||||||
X wrapped_ ;
|
|
||||||
|
|
||||||
public:
|
|
||||||
|
|
||||||
W ( X const& x ) : wrapped_(x) {}
|
|
||||||
|
|
||||||
template< class InPlaceFactory >
|
|
||||||
W ( InPlaceFactory const& fac ) { fac.template <X>construct(&wrapped_) ; }
|
|
||||||
|
|
||||||
} ;
|
|
||||||
|
|
||||||
void foo()
|
|
||||||
{
|
|
||||||
// Wrapped object constructed in-place via a InPlaceFactory.
|
|
||||||
// No temporary created.
|
|
||||||
W ( in_place(123,"hello") ) ;
|
|
||||||
}
|
|
||||||
|
|
||||||
The factories are implemented in the headers: __IN_PLACE_FACTORY_HPP__ and __TYPED_IN_PLACE_FACTORY_HPP__
|
|
||||||
|
|
||||||
[endsect]
|
|
||||||
|
|
||||||
[section A note about optional<bool>]
|
|
||||||
|
|
||||||
`optional<bool>` should be used with special caution and consideration.
|
|
||||||
|
|
||||||
First, it is functionally similar to a tristate boolean (false, maybe, true)
|
|
||||||
—such as __BOOST_TRIBOOL__— except that in a tristate boolean, the maybe state
|
|
||||||
[_represents a valid value], unlike the corresponding state of an uninitialized
|
|
||||||
`optional<bool>`.
|
|
||||||
It should be carefully considered if an `optional<bool>` instead of a `tribool`
|
|
||||||
is really needed.
|
|
||||||
|
|
||||||
Second, although `optional<>` provides a contextual conversion to `bool` in C++11,
|
|
||||||
this falls back to an implicit conversion on older compilers. This conversion refers
|
|
||||||
to the initialization state and not to the contained value. Using `optional<bool>`
|
|
||||||
can lead to subtle errors due to the implicit `bool` conversion:
|
|
||||||
|
|
||||||
void foo ( bool v ) ;
|
|
||||||
void bar()
|
|
||||||
{
|
|
||||||
optional<bool> v = try();
|
|
||||||
|
|
||||||
// The following intended to pass the value of 'v' to foo():
|
|
||||||
foo(v);
|
|
||||||
// But instead, the initialization state is passed
|
|
||||||
// due to a typo: it should have been foo(*v).
|
|
||||||
}
|
|
||||||
|
|
||||||
The only implicit conversion is to `bool`, and it is safe in the sense that
|
|
||||||
typical integral promotions don't apply (i.e. if `foo()` takes an `int`
|
|
||||||
instead, it won't compile).
|
|
||||||
|
|
||||||
Third, mixed comparisons with `bool` work differently than similar mixed comparisons between pointers and `bool`, so the results might surprise you:
|
|
||||||
|
|
||||||
optional<bool> oEmpty(none), oTrue(true), oFalse(false);
|
|
||||||
|
|
||||||
if (oEmpty == none); // renders true
|
|
||||||
if (oEmpty == false); // renders false!
|
|
||||||
if (oEmpty == true); // renders false!
|
|
||||||
|
|
||||||
if (oFalse == none); // renders false
|
|
||||||
if (oFalse == false); // renders true!
|
|
||||||
if (oFalse == true); // renders false
|
|
||||||
|
|
||||||
if (oTrue == none); // renders false
|
|
||||||
if (oTrue == false); // renders false
|
|
||||||
if (oTrue == true); // renders true
|
|
||||||
|
|
||||||
In other words, for `optional<>`, the following assertion does not hold:
|
|
||||||
|
|
||||||
assert((opt == false) == (!opt));
|
|
||||||
[endsect]
|
|
||||||
|
|
||||||
[section Exception Safety Guarantees]
|
|
||||||
|
|
||||||
This library assumes that `T`'s destructor does not throw exceptions. If it does, the behaviour of many operations on `optional<T>` is undefined.
|
|
||||||
|
|
||||||
The following mutating operations never throw exceptions:
|
|
||||||
|
|
||||||
* `optional<T>::operator= ( none_t ) noexcept`
|
|
||||||
* `optional<T>::reset() noexcept`
|
|
||||||
|
|
||||||
In addition, the following constructors and the destructor never throw exceptions:
|
|
||||||
|
|
||||||
* `optional<T>::optional() noexcept`
|
|
||||||
* `optional<T>::optional( none_t ) noexcept`
|
|
||||||
|
|
||||||
|
|
||||||
Regarding the following assignment functions:
|
|
||||||
|
|
||||||
* `optional<T>::operator= ( optional<T> const& )`
|
|
||||||
* `optional<T>::operator= ( T const& )`
|
|
||||||
* `template<class U> optional<T>::operator= ( optional<U> const& )`
|
|
||||||
* `template<class InPlaceFactory> optional<T>::operator= ( InPlaceFactory const& )`
|
|
||||||
* `template<class TypedInPlaceFactory> optional<T>::operator= ( TypedInPlaceFactory const& ) `
|
|
||||||
* `optional<T>::reset( T const& )`
|
|
||||||
|
|
||||||
They forward calls to the corresponding `T`'s constructors or assignments (depending on whether the optional object is initialized or not); so if both `T`'s constructor and the assignment provide strong exception safety guarantee, `optional<T>`'s assignment also provides strong exception safety guarantee; otherwise we only get the basic guarantee. Additionally, if both involved `T`'s constructor and the assignment never throw, `optional<T>`'s assignment also never throws.
|
|
||||||
|
|
||||||
Unless `T`'s constructor or assignment throws, assignments to `optional<T>` do not throw anything else on its own. A throw during assignment never changes the initialization state of any optional object involved:
|
|
||||||
|
|
||||||
|
|
||||||
optional<T> opt1(val1);
|
|
||||||
optional<T> opt2(val2);
|
|
||||||
assert(opt1);
|
|
||||||
assert(opt2);
|
|
||||||
|
|
||||||
try
|
|
||||||
{
|
|
||||||
opt1 = opt2; // throws
|
|
||||||
}
|
|
||||||
catch(...)
|
|
||||||
{
|
|
||||||
assert(opt1);
|
|
||||||
assert(opt2);
|
|
||||||
}
|
|
||||||
|
|
||||||
This also applies to move assignments/constructors. However, move operations are made no-throw more often.
|
|
||||||
|
|
||||||
Operation `emplace` provides basic exception safety guarantee. If it throws, the optional object becomes uninitialized regardless of its initial state, and its previous contained value (if any) is destroyed. It doesn't call any assignment or move/copy constructor on `T`.
|
|
||||||
|
|
||||||
[heading Swap]
|
|
||||||
|
|
||||||
Unless `swap` on optional is customized, its primary implementation forwards calls to `T`'s `swap` or move constructor (depending on the initialization state of the optional objects). Thus, if both `T`'s `swap` and move constructor never throw, `swap` on `optional<T>` never throws. similarly, if both `T`'s `swap` and move constructor offer strong guarantee, `swap` on `optional<T>` also offers a strong guarantee.
|
|
||||||
|
|
||||||
In case `swap` on optional is customized, the call to `T`'s move constructor are replaced with the calls to `T`'s default constructor followed by `swap`. (This is more useful on older compilers that do not support move semantics, when one wants to acheive stronger exception safety guarantees.) In this case the exception safety guarantees for `swap` are reliant on the guarantees of `T`'s `swap` and default constructor
|
|
||||||
[endsect]
|
|
||||||
|
|
||||||
[section Type requirements]
|
|
||||||
|
|
||||||
At the very minimum for `optional<T>` to work with a minimum interface it is required that `T` has a publicly accessible no-throw destructor. In that case you need to initialize the optional object with function `emplace()` or use [*InPlaceFactories].
|
|
||||||
Additionally, if `T` is `Moveable`, `optional<T>` is also `Moveable` and can be easily initialized from an rvalue of type `T` and be passed by value.
|
|
||||||
Additionally if `T` is `Copyable`, `optional<T>` is also `Copyable` and can be easily initialized from an lvalue of type `T`.
|
|
||||||
|
|
||||||
`T` [_is not] required to be __SGI_DEFAULT_CONSTRUCTIBLE__.
|
|
||||||
|
|
||||||
[endsect]
|
|
||||||
|
|
||||||
|
|
@ -9,7 +9,7 @@
|
|||||||
http://www.boost.org/LICENSE_1_0.txt)
|
http://www.boost.org/LICENSE_1_0.txt)
|
||||||
]
|
]
|
||||||
|
|
||||||
[section Discussion]
|
[section Motivation]
|
||||||
|
|
||||||
Consider these functions which should return a value but which might not have
|
Consider these functions which should return a value but which might not have
|
||||||
a value to return:
|
a value to return:
|
||||||
@ -77,4 +77,4 @@ without ever checking if it has a valid value.
|
|||||||
|
|
||||||
Clearly, we need a better idiom.
|
Clearly, we need a better idiom.
|
||||||
|
|
||||||
[endsect]
|
[endsect]
|
@ -8,7 +8,7 @@
|
|||||||
http://www.boost.org/LICENSE_1_0.txt)
|
http://www.boost.org/LICENSE_1_0.txt)
|
||||||
]
|
]
|
||||||
|
|
||||||
[section Development]
|
[section Design Overview]
|
||||||
|
|
||||||
[section The models]
|
[section The models]
|
||||||
|
|
139
doc/15_in_place_factories.qbk
Normal file
139
doc/15_in_place_factories.qbk
Normal file
@ -0,0 +1,139 @@
|
|||||||
|
|
||||||
|
[section In-Place Factories]
|
||||||
|
|
||||||
|
One of the typical problems with wrappers and containers is that their
|
||||||
|
interfaces usually provide an operation to initialize or assign the
|
||||||
|
contained object as a copy of some other object. This not only requires the
|
||||||
|
underlying type to be __COPY_CONSTRUCTIBLE__, but also requires the existence of
|
||||||
|
a fully constructed object, often temporary, just to follow the copy from:
|
||||||
|
|
||||||
|
struct X
|
||||||
|
{
|
||||||
|
X ( int, std::string ) ;
|
||||||
|
} ;
|
||||||
|
|
||||||
|
class W
|
||||||
|
{
|
||||||
|
X wrapped_ ;
|
||||||
|
|
||||||
|
public:
|
||||||
|
|
||||||
|
W ( X const& x ) : wrapped_(x) {}
|
||||||
|
} ;
|
||||||
|
|
||||||
|
void foo()
|
||||||
|
{
|
||||||
|
// Temporary object created.
|
||||||
|
W ( X(123,"hello") ) ;
|
||||||
|
}
|
||||||
|
|
||||||
|
A solution to this problem is to support direct construction of the
|
||||||
|
contained object right in the container's storage.
|
||||||
|
In this scheme, the user only needs to supply the arguments to the
|
||||||
|
constructor to use in the wrapped object construction.
|
||||||
|
|
||||||
|
class W
|
||||||
|
{
|
||||||
|
X wrapped_ ;
|
||||||
|
|
||||||
|
public:
|
||||||
|
|
||||||
|
W ( X const& x ) : wrapped_(x) {}
|
||||||
|
W ( int a0, std::string a1) : wrapped_(a0,a1) {}
|
||||||
|
} ;
|
||||||
|
|
||||||
|
void foo()
|
||||||
|
{
|
||||||
|
// Wrapped object constructed in-place
|
||||||
|
// No temporary created.
|
||||||
|
W (123,"hello") ;
|
||||||
|
}
|
||||||
|
|
||||||
|
A limitation of this method is that it doesn't scale well to wrapped
|
||||||
|
objects with multiple constructors nor to generic code were the constructor
|
||||||
|
overloads are unknown.
|
||||||
|
|
||||||
|
The solution presented in this library is the family of [*InPlaceFactories]
|
||||||
|
and [*TypedInPlaceFactories].
|
||||||
|
These factories are a family of classes which encapsulate an increasing
|
||||||
|
number of arbitrary constructor parameters and supply a method to construct
|
||||||
|
an object of a given type using those parameters at an address specified by
|
||||||
|
the user via placement new.
|
||||||
|
|
||||||
|
For example, one member of this family looks like:
|
||||||
|
|
||||||
|
template<class T,class A0, class A1>
|
||||||
|
class TypedInPlaceFactory2
|
||||||
|
{
|
||||||
|
A0 m_a0 ; A1 m_a1 ;
|
||||||
|
|
||||||
|
public:
|
||||||
|
|
||||||
|
TypedInPlaceFactory2( A0 const& a0, A1 const& a1 ) : m_a0(a0), m_a1(a1) {}
|
||||||
|
|
||||||
|
void construct ( void* p ) { new (p) T(m_a0,m_a1) ; }
|
||||||
|
} ;
|
||||||
|
|
||||||
|
A wrapper class aware of this can use it as:
|
||||||
|
|
||||||
|
class W
|
||||||
|
{
|
||||||
|
X wrapped_ ;
|
||||||
|
|
||||||
|
public:
|
||||||
|
|
||||||
|
W ( X const& x ) : wrapped_(x) {}
|
||||||
|
W ( TypedInPlaceFactory2 const& fac ) { fac.construct(&wrapped_) ; }
|
||||||
|
} ;
|
||||||
|
|
||||||
|
void foo()
|
||||||
|
{
|
||||||
|
// Wrapped object constructed in-place via a TypedInPlaceFactory.
|
||||||
|
// No temporary created.
|
||||||
|
W ( TypedInPlaceFactory2<X,int,std::string>(123,"hello")) ;
|
||||||
|
}
|
||||||
|
|
||||||
|
The factories are divided in two groups:
|
||||||
|
|
||||||
|
* [_TypedInPlaceFactories]: those which take the target type as a primary
|
||||||
|
template parameter.
|
||||||
|
* [_InPlaceFactories]: those with a template `construct(void*)` member
|
||||||
|
function taking the target type.
|
||||||
|
|
||||||
|
Within each group, all the family members differ only in the number of
|
||||||
|
parameters allowed.
|
||||||
|
|
||||||
|
This library provides an overloaded set of helper template functions to
|
||||||
|
construct these factories without requiring unnecessary template parameters:
|
||||||
|
|
||||||
|
template<class A0,...,class AN>
|
||||||
|
InPlaceFactoryN <A0,...,AN> in_place ( A0 const& a0, ..., AN const& aN) ;
|
||||||
|
|
||||||
|
template<class T,class A0,...,class AN>
|
||||||
|
TypedInPlaceFactoryN <T,A0,...,AN> in_place ( T const& a0, A0 const& a0, ..., AN const& aN) ;
|
||||||
|
|
||||||
|
In-place factories can be used generically by the wrapper and user as follows:
|
||||||
|
|
||||||
|
class W
|
||||||
|
{
|
||||||
|
X wrapped_ ;
|
||||||
|
|
||||||
|
public:
|
||||||
|
|
||||||
|
W ( X const& x ) : wrapped_(x) {}
|
||||||
|
|
||||||
|
template< class InPlaceFactory >
|
||||||
|
W ( InPlaceFactory const& fac ) { fac.template <X>construct(&wrapped_) ; }
|
||||||
|
|
||||||
|
} ;
|
||||||
|
|
||||||
|
void foo()
|
||||||
|
{
|
||||||
|
// Wrapped object constructed in-place via a InPlaceFactory.
|
||||||
|
// No temporary created.
|
||||||
|
W ( in_place(123,"hello") ) ;
|
||||||
|
}
|
||||||
|
|
||||||
|
The factories are implemented in the headers: __IN_PLACE_FACTORY_HPP__ and __TYPED_IN_PLACE_FACTORY_HPP__
|
||||||
|
|
||||||
|
[endsect]
|
52
doc/16_optional_bool.qbk
Normal file
52
doc/16_optional_bool.qbk
Normal file
@ -0,0 +1,52 @@
|
|||||||
|
|
||||||
|
[section A note about optional<bool>]
|
||||||
|
|
||||||
|
`optional<bool>` should be used with special caution and consideration.
|
||||||
|
|
||||||
|
First, it is functionally similar to a tristate boolean (false, maybe, true)
|
||||||
|
—such as __BOOST_TRIBOOL__— except that in a tristate boolean, the maybe state
|
||||||
|
[_represents a valid value], unlike the corresponding state of an uninitialized
|
||||||
|
`optional<bool>`.
|
||||||
|
It should be carefully considered if an `optional<bool>` instead of a `tribool`
|
||||||
|
is really needed.
|
||||||
|
|
||||||
|
Second, although `optional<>` provides a contextual conversion to `bool` in C++11,
|
||||||
|
this falls back to an implicit conversion on older compilers. This conversion refers
|
||||||
|
to the initialization state and not to the contained value. Using `optional<bool>`
|
||||||
|
can lead to subtle errors due to the implicit `bool` conversion:
|
||||||
|
|
||||||
|
void foo ( bool v ) ;
|
||||||
|
void bar()
|
||||||
|
{
|
||||||
|
optional<bool> v = try();
|
||||||
|
|
||||||
|
// The following intended to pass the value of 'v' to foo():
|
||||||
|
foo(v);
|
||||||
|
// But instead, the initialization state is passed
|
||||||
|
// due to a typo: it should have been foo(*v).
|
||||||
|
}
|
||||||
|
|
||||||
|
The only implicit conversion is to `bool`, and it is safe in the sense that
|
||||||
|
typical integral promotions don't apply (i.e. if `foo()` takes an `int`
|
||||||
|
instead, it won't compile).
|
||||||
|
|
||||||
|
Third, mixed comparisons with `bool` work differently than similar mixed comparisons between pointers and `bool`, so the results might surprise you:
|
||||||
|
|
||||||
|
optional<bool> oEmpty(none), oTrue(true), oFalse(false);
|
||||||
|
|
||||||
|
if (oEmpty == none); // renders true
|
||||||
|
if (oEmpty == false); // renders false!
|
||||||
|
if (oEmpty == true); // renders false!
|
||||||
|
|
||||||
|
if (oFalse == none); // renders false
|
||||||
|
if (oFalse == false); // renders true!
|
||||||
|
if (oFalse == true); // renders false
|
||||||
|
|
||||||
|
if (oTrue == none); // renders false
|
||||||
|
if (oTrue == false); // renders false
|
||||||
|
if (oTrue == true); // renders true
|
||||||
|
|
||||||
|
In other words, for `optional<>`, the following assertion does not hold:
|
||||||
|
|
||||||
|
assert((opt == false) == (!opt));
|
||||||
|
[endsect]
|
57
doc/17_exception_safety.qbk
Normal file
57
doc/17_exception_safety.qbk
Normal file
@ -0,0 +1,57 @@
|
|||||||
|
|
||||||
|
[section Exception Safety Guarantees]
|
||||||
|
|
||||||
|
This library assumes that `T`'s destructor does not throw exceptions. If it does, the behaviour of many operations on `optional<T>` is undefined.
|
||||||
|
|
||||||
|
The following mutating operations never throw exceptions:
|
||||||
|
|
||||||
|
* `optional<T>::operator= ( none_t ) noexcept`
|
||||||
|
* `optional<T>::reset() noexcept`
|
||||||
|
|
||||||
|
In addition, the following constructors and the destructor never throw exceptions:
|
||||||
|
|
||||||
|
* `optional<T>::optional() noexcept`
|
||||||
|
* `optional<T>::optional( none_t ) noexcept`
|
||||||
|
|
||||||
|
|
||||||
|
Regarding the following assignment functions:
|
||||||
|
|
||||||
|
* `optional<T>::operator= ( optional<T> const& )`
|
||||||
|
* `optional<T>::operator= ( T const& )`
|
||||||
|
* `template<class U> optional<T>::operator= ( optional<U> const& )`
|
||||||
|
* `template<class InPlaceFactory> optional<T>::operator= ( InPlaceFactory const& )`
|
||||||
|
* `template<class TypedInPlaceFactory> optional<T>::operator= ( TypedInPlaceFactory const& ) `
|
||||||
|
* `optional<T>::reset( T const& )`
|
||||||
|
|
||||||
|
They forward calls to the corresponding `T`'s constructors or assignments (depending on whether the optional object is initialized or not); so if both `T`'s constructor and the assignment provide strong exception safety guarantee, `optional<T>`'s assignment also provides strong exception safety guarantee; otherwise we only get the basic guarantee. Additionally, if both involved `T`'s constructor and the assignment never throw, `optional<T>`'s assignment also never throws.
|
||||||
|
|
||||||
|
Unless `T`'s constructor or assignment throws, assignments to `optional<T>` do not throw anything else on its own. A throw during assignment never changes the initialization state of any optional object involved:
|
||||||
|
|
||||||
|
|
||||||
|
optional<T> opt1(val1);
|
||||||
|
optional<T> opt2(val2);
|
||||||
|
assert(opt1);
|
||||||
|
assert(opt2);
|
||||||
|
|
||||||
|
try
|
||||||
|
{
|
||||||
|
opt1 = opt2; // throws
|
||||||
|
}
|
||||||
|
catch(...)
|
||||||
|
{
|
||||||
|
assert(opt1);
|
||||||
|
assert(opt2);
|
||||||
|
}
|
||||||
|
|
||||||
|
This also applies to move assignments/constructors. However, move operations are made no-throw more often.
|
||||||
|
|
||||||
|
Operation `emplace` provides basic exception safety guarantee. If it throws, the optional object becomes uninitialized regardless of its initial state, and its previous contained value (if any) is destroyed. It doesn't call any assignment or move/copy constructor on `T`.
|
||||||
|
|
||||||
|
[heading Swap]
|
||||||
|
|
||||||
|
Unless `swap` on optional is customized, its primary implementation forwards calls to `T`'s `swap` or move constructor (depending on the initialization state of the optional objects). Thus, if both `T`'s `swap` and move constructor never throw, `swap` on `optional<T>` never throws. similarly, if both `T`'s `swap` and move constructor offer strong guarantee, `swap` on `optional<T>` also offers a strong guarantee.
|
||||||
|
|
||||||
|
In case `swap` on optional is customized, the call to `T`'s move constructor are replaced with the calls to `T`'s default constructor followed by `swap`. (This is more useful on older compilers that do not support move semantics, when one wants to acheive stronger exception safety guarantees.) In this case the exception safety guarantees for `swap` are reliant on the guarantees of `T`'s `swap` and default constructor
|
||||||
|
[endsect]
|
||||||
|
|
||||||
|
|
10
doc/18_type_requirements.qbk
Normal file
10
doc/18_type_requirements.qbk
Normal file
@ -0,0 +1,10 @@
|
|||||||
|
|
||||||
|
[section Type requirements]
|
||||||
|
|
||||||
|
At the very minimum for `optional<T>` to work with a minimum interface it is required that `T` has a publicly accessible no-throw destructor. In that case you need to initialize the optional object with function `emplace()` or use [*InPlaceFactories].
|
||||||
|
Additionally, if `T` is `Moveable`, `optional<T>` is also `Moveable` and can be easily initialized from an rvalue of type `T` and be passed by value.
|
||||||
|
Additionally, if `T` is `Copyable`, `optional<T>` is also `Copyable` and can be easily initialized from an lvalue of type `T`.
|
||||||
|
|
||||||
|
`T` [_is not] required to be __SGI_DEFAULT_CONSTRUCTIBLE__.
|
||||||
|
|
||||||
|
[endsect]
|
@ -71,13 +71,16 @@
|
|||||||
T const* operator ->() const ; ``[link reference_optional_operator_arrow __GO_TO__]``
|
T const* operator ->() const ; ``[link reference_optional_operator_arrow __GO_TO__]``
|
||||||
T* operator ->() ; ``[link reference_optional_operator_arrow __GO_TO__]``
|
T* operator ->() ; ``[link reference_optional_operator_arrow __GO_TO__]``
|
||||||
|
|
||||||
T const& operator *() const ; ``[link reference_optional_get __GO_TO__]``
|
T const& operator *() const& ; ``[link reference_optional_operator_asterisk __GO_TO__]``
|
||||||
T& operator *() ; ``[link reference_optional_get __GO_TO__]``
|
T& operator *() &; ``[link reference_optional_operator_asterisk __GO_TO__]``
|
||||||
|
T&& operator *() &&; ``[link reference_optional_operator_asterisk __GO_TO__]``
|
||||||
|
|
||||||
T const& value() const ; ``[link reference_optional_value __GO_TO__]``
|
T const& value() const& ; ``[link reference_optional_value __GO_TO__]``
|
||||||
T& value() ; ``[link reference_optional_value __GO_TO__]``
|
T& value() & ; ``[link reference_optional_value __GO_TO__]``
|
||||||
|
T&& value() && ; ``[link reference_optional_value __GO_TO__]``
|
||||||
|
|
||||||
template<class U> T value_or( U && v ) const ; ``[link reference_optional_value_or __GO_TO__]``
|
template<class U> T value_or( U && v ) const& ; ``[link reference_optional_value_or __GO_TO__]``
|
||||||
|
template<class U> T value_or( U && v ) && ; ``[link reference_optional_value_or __GO_TO__]``
|
||||||
|
|
||||||
T const* get_ptr() const ; ``[link reference_optional_get_ptr __GO_TO__]``
|
T const* get_ptr() const ; ``[link reference_optional_get_ptr __GO_TO__]``
|
||||||
T* get_ptr() ; ``[link reference_optional_get_ptr __GO_TO__]``
|
T* get_ptr() ; ``[link reference_optional_get_ptr __GO_TO__]``
|
||||||
@ -467,7 +470,7 @@ factory.
|
|||||||
* [*Postconditions: ] `*this` is [_initialized] and its value is ['directly given]
|
* [*Postconditions: ] `*this` is [_initialized] and its value is ['directly given]
|
||||||
from the factory `f` (i.e., the value [_is not copied]).
|
from the factory `f` (i.e., the value [_is not copied]).
|
||||||
* [*Throws:] Whatever the `T` constructor called by the factory throws.
|
* [*Throws:] Whatever the `T` constructor called by the factory throws.
|
||||||
* [*Notes:] See [link boost_optional.in_place_factories In-Place Factories]
|
* [*Notes:] See [link boost_optional.tutorial.in_place_factories In-Place Factories]
|
||||||
* [*Exception Safety:] Exceptions can only be thrown during the call to
|
* [*Exception Safety:] Exceptions can only be thrown during the call to
|
||||||
the `T` constructor used by the factory; in that case, this constructor has
|
the `T` constructor used by the factory; in that case, this constructor has
|
||||||
no effect.
|
no effect.
|
||||||
@ -530,7 +533,7 @@ __SPACE__
|
|||||||
* [*Postconditions: ] `*this` is initialized and it references the same
|
* [*Postconditions: ] `*this` is initialized and it references the same
|
||||||
object referenced by `rhs`.
|
object referenced by `rhs`.
|
||||||
* [*Notes:] If `*this` was initialized, it is ['rebound] to the new object.
|
* [*Notes:] If `*this` was initialized, it is ['rebound] to the new object.
|
||||||
See [link boost_optional.rebinding_semantics_for_assignment_of_optional_references here] for details on this behavior.
|
See [link boost_optional.tutorial.rebinding_semantics_for_assignment_of_optional_references here] for details on this behavior.
|
||||||
* [*Example:]
|
* [*Example:]
|
||||||
``
|
``
|
||||||
int a = 1 ;
|
int a = 1 ;
|
||||||
@ -625,7 +628,7 @@ __SPACE__
|
|||||||
references the same object referenced by `*rhs`; otherwise, `*this` is
|
references the same object referenced by `*rhs`; otherwise, `*this` is
|
||||||
uninitialized (and references no object).
|
uninitialized (and references no object).
|
||||||
* [*Notes:] If `*this` was initialized and so is `*rhs`, `*this` is ['rebound] to
|
* [*Notes:] If `*this` was initialized and so is `*rhs`, `*this` is ['rebound] to
|
||||||
the new object. See [link boost_optional.rebinding_semantics_for_assignment_of_optional_references here] for details on this behavior.
|
the new object. See [link boost_optional.tutorial.rebinding_semantics_for_assignment_of_optional_references here] for details on this behavior.
|
||||||
* [*Example:]
|
* [*Example:]
|
||||||
``
|
``
|
||||||
int a = 1 ;
|
int a = 1 ;
|
||||||
@ -773,7 +776,7 @@ factory.
|
|||||||
* [*Postconditions: ] `*this` is [_initialized] and its value is ['directly given]
|
* [*Postconditions: ] `*this` is [_initialized] and its value is ['directly given]
|
||||||
from the factory `f` (i.e., the value [_is not copied]).
|
from the factory `f` (i.e., the value [_is not copied]).
|
||||||
* [*Throws:] Whatever the `T` constructor called by the factory throws.
|
* [*Throws:] Whatever the `T` constructor called by the factory throws.
|
||||||
* [*Notes:] See [link boost_optional.in_place_factories In-Place Factories]
|
* [*Notes:] See [link boost_optional.tutorial.in_place_factories In-Place Factories]
|
||||||
* [*Exception Safety:] Exceptions can only be thrown during the call to
|
* [*Exception Safety:] Exceptions can only be thrown during the call to
|
||||||
the `T` constructor used by the factory; in that case, the `optional` object
|
the `T` constructor used by the factory; in that case, the `optional` object
|
||||||
will be reset to be ['uninitialized].
|
will be reset to be ['uninitialized].
|
||||||
@ -790,14 +793,12 @@ __SPACE__
|
|||||||
[#reference_optional_reset]
|
[#reference_optional_reset]
|
||||||
|
|
||||||
[: `void optional<T>::reset() noexcept ;`]
|
[: `void optional<T>::reset() noexcept ;`]
|
||||||
* [*Deprecated:] Same as `operator=( detail::none_t );`
|
* [*Deprecated:] Same as `operator=( none_t );`
|
||||||
|
|
||||||
__SPACE__
|
__SPACE__
|
||||||
|
|
||||||
[#reference_optional_get]
|
[#reference_optional_get]
|
||||||
|
|
||||||
[: `T const& optional<T` ['(not a ref)]`>::operator*() const ;`]
|
|
||||||
[: `T& optional<T` ['(not a ref)]`>::operator*();`]
|
|
||||||
[: `T const& optional<T` ['(not a ref)]`>::get() const ;`]
|
[: `T const& optional<T` ['(not a ref)]`>::get() const ;`]
|
||||||
[: `T& optional<T` ['(not a ref)]`>::get() ;`]
|
[: `T& optional<T` ['(not a ref)]`>::get() ;`]
|
||||||
|
|
||||||
@ -808,6 +809,32 @@ __SPACE__
|
|||||||
* [*Returns:] A reference to the contained value
|
* [*Returns:] A reference to the contained value
|
||||||
* [*Throws:] Nothing.
|
* [*Throws:] Nothing.
|
||||||
* [*Notes:] The requirement is asserted via `BOOST_ASSERT()`.
|
* [*Notes:] The requirement is asserted via `BOOST_ASSERT()`.
|
||||||
|
|
||||||
|
__SPACE__
|
||||||
|
|
||||||
|
[: `T const& optional<T&>::get() const ;`]
|
||||||
|
[: `T& optional<T&>::get() ;`]
|
||||||
|
|
||||||
|
[: `inline T const& get ( optional<T&> const& ) ;`]
|
||||||
|
[: `inline T& get ( optional<T&> &) ;`]
|
||||||
|
|
||||||
|
* [*Requires: ] `*this` is initialized
|
||||||
|
* [*Returns:] [_The] reference contained.
|
||||||
|
* [*Throws:] Nothing.
|
||||||
|
* [*Notes:] The requirement is asserted via `BOOST_ASSERT()`.
|
||||||
|
|
||||||
|
__SPACE__
|
||||||
|
|
||||||
|
[#reference_optional_operator_asterisk]
|
||||||
|
|
||||||
|
[: `T const& optional<T` ['(not a ref)]`>::operator*() const& ;`]
|
||||||
|
[: `T& optional<T` ['(not a ref)]`>::operator*() &;`]
|
||||||
|
[: `T&& optional<T` ['(not a ref)]`>::operator*() &&;`]
|
||||||
|
|
||||||
|
* [*Requires:] `*this` is initialized
|
||||||
|
* [*Returns:] A reference to the contained value
|
||||||
|
* [*Throws:] Nothing.
|
||||||
|
* [*Notes:] The requirement is asserted via `BOOST_ASSERT()`. On compilers that do not support ref-qualifiers on member functions these three overloads are replaced with the classical two: a `const` and non-`const` member functions.
|
||||||
* [*Example:]
|
* [*Example:]
|
||||||
``
|
``
|
||||||
T v ;
|
T v ;
|
||||||
@ -821,14 +848,36 @@ assert ( *opt == w ) ;
|
|||||||
|
|
||||||
__SPACE__
|
__SPACE__
|
||||||
|
|
||||||
|
[: `T const& optional<T&>::operator*() const& ;`]
|
||||||
|
[: `T & optional<T&>::operator*() & ;`]
|
||||||
|
[: `T & optional<T&>::operator*() && ;`]
|
||||||
|
|
||||||
|
* [*Requires: ] `*this` is initialized
|
||||||
|
* [*Returns:] [_The] reference contained.
|
||||||
|
* [*Throws:] Nothing.
|
||||||
|
* [*Notes:] The requirement is asserted via `BOOST_ASSERT()`. On compilers that do not support ref-qualifiers on member functions these three overloads are replaced with the classical two: a `const` and non-`const` member functions.
|
||||||
|
* [*Example:]
|
||||||
|
``
|
||||||
|
T v ;
|
||||||
|
T& vref = v ;
|
||||||
|
optional<T&> opt ( vref );
|
||||||
|
T const& vref2 = *opt;
|
||||||
|
assert ( vref2 == v ) ;
|
||||||
|
++ v ;
|
||||||
|
assert ( *opt == v ) ;
|
||||||
|
``
|
||||||
|
|
||||||
|
__SPACE__
|
||||||
|
|
||||||
[#reference_optional_value]
|
[#reference_optional_value]
|
||||||
|
|
||||||
[: `T const& optional<T>::value() const ;`]
|
[: `T const& optional<T>::value() const& ;`]
|
||||||
[: `T& optional<T>::value();`]
|
[: `T& optional<T>::value() & ;`]
|
||||||
|
[: `T&& optional<T>::value() && ;`]
|
||||||
|
|
||||||
* [*Returns:] A reference to the contained value, if `*this` is initialized.
|
* [*Returns:] A reference to the contained value, if `*this` is initialized.
|
||||||
* [*Throws:] An instance of `bad_optional_access`, if `*this` is not initialized.
|
* [*Throws:] An instance of `bad_optional_access`, if `*this` is not initialized.
|
||||||
|
* [*Notes:] On compilers that do not support ref-qualifiers on member functions these three overloads are replaced with the classical two: a `const` and non-`const` member functions.
|
||||||
* [*Example:]
|
* [*Example:]
|
||||||
``
|
``
|
||||||
T v ;
|
T v ;
|
||||||
@ -848,12 +897,13 @@ __SPACE__
|
|||||||
|
|
||||||
[#reference_optional_value_or]
|
[#reference_optional_value_or]
|
||||||
|
|
||||||
[: `template<class U> T optional<T>::value_or(U && v) const ;`]
|
[: `template<class U> T optional<T>::value_or(U && v) const& ;`]
|
||||||
|
[: `template<class U> T optional<T>::value_or(U && v) && ;`]
|
||||||
|
|
||||||
* [*Requires:] `T` is CopyConstructible.
|
* [*Requires:] `T` is CopyConstructible.
|
||||||
* [*Returns:] `bool(*this) ? **this : static_cast<T>(forward<U>(v))`.
|
* [*Returns:] First overload: `bool(*this) ? **this : static_cast<T>(forward<U>(v))`. second overload: `bool(*this) ? std::move(**this) : static_cast<T>(forward<U>(v))`.
|
||||||
* [*Throws:] Any exception thrown by the selected constructor of `T`.
|
* [*Throws:] Any exception thrown by the selected constructor of `T`.
|
||||||
* [*Notes:] On compilers without rvalue reference support the type of `v` becomes `U const&`.
|
* [*Notes:] On compilers that do not support ref-qualifiers on member functions these three overloads are replaced with the classical two: a `const` and non-`const` member functions. On compilers without rvalue reference support the type of `v` becomes `U const&`.
|
||||||
|
|
||||||
__SPACE__
|
__SPACE__
|
||||||
|
|
||||||
@ -881,30 +931,6 @@ assert ( u == v ) ;
|
|||||||
assert ( u != z ) ;
|
assert ( u != z ) ;
|
||||||
``
|
``
|
||||||
|
|
||||||
__SPACE__
|
|
||||||
|
|
||||||
[: `T const& optional<T&>::operator*() const ;`]
|
|
||||||
[: `T & optional<T&>::operator*();`]
|
|
||||||
[: `T const& optional<T&>::get() const ;`]
|
|
||||||
[: `T& optional<T&>::get() ;`]
|
|
||||||
|
|
||||||
[: `inline T const& get ( optional<T&> const& ) ;`]
|
|
||||||
[: `inline T& get ( optional<T&> &) ;`]
|
|
||||||
|
|
||||||
* [*Requires: ] `*this` is initialized
|
|
||||||
* [*Returns:] [_The] reference contained.
|
|
||||||
* [*Throws:] Nothing.
|
|
||||||
* [*Notes:] The requirement is asserted via `BOOST_ASSERT()`.
|
|
||||||
* [*Example:]
|
|
||||||
``
|
|
||||||
T v ;
|
|
||||||
T& vref = v ;
|
|
||||||
optional<T&> opt ( vref );
|
|
||||||
T const& vref2 = *opt;
|
|
||||||
assert ( vref2 == v ) ;
|
|
||||||
++ v ;
|
|
||||||
assert ( *opt == v ) ;
|
|
||||||
``
|
|
||||||
|
|
||||||
__SPACE__
|
__SPACE__
|
||||||
|
|
@ -27,7 +27,8 @@ boostbook standalone
|
|||||||
<xsl:param>boost.root=../../../..
|
<xsl:param>boost.root=../../../..
|
||||||
<xsl:param>toc.max.depth=2
|
<xsl:param>toc.max.depth=2
|
||||||
<xsl:param>toc.section.depth=2
|
<xsl:param>toc.section.depth=2
|
||||||
<xsl:param>chunk.section.depth=1
|
<xsl:param>chunk.first.sections=2
|
||||||
|
<xsl:param>chunk.section.depth=2
|
||||||
<format>pdf:<xsl:param>img.src.path=$(images)/
|
<format>pdf:<xsl:param>img.src.path=$(images)/
|
||||||
<format>pdf:<xsl:param>boost.url.prefix=http://www.boost.org/doc/libs/release/libs/optional/doc/html
|
<format>pdf:<xsl:param>boost.url.prefix=http://www.boost.org/doc/libs/release/libs/optional/doc/html
|
||||||
;
|
;
|
||||||
|
@ -6,7 +6,7 @@
|
|||||||
<meta name="generator" content="DocBook XSL Stylesheets V1.78.1">
|
<meta name="generator" content="DocBook XSL Stylesheets V1.78.1">
|
||||||
<link rel="home" href="../index.html" title="Chapter 1. Boost.Optional">
|
<link rel="home" href="../index.html" title="Chapter 1. Boost.Optional">
|
||||||
<link rel="up" href="../index.html" title="Chapter 1. Boost.Optional">
|
<link rel="up" href="../index.html" title="Chapter 1. Boost.Optional">
|
||||||
<link rel="prev" href="in_place_factories.html" title="In-Place Factories">
|
<link rel="prev" href="detailed_semantics.html" title="Detailed Semantics">
|
||||||
<link rel="next" href="exception_safety_guarantees.html" title="Exception Safety Guarantees">
|
<link rel="next" href="exception_safety_guarantees.html" title="Exception Safety Guarantees">
|
||||||
</head>
|
</head>
|
||||||
<body bgcolor="white" text="black" link="#0000FF" vlink="#840084" alink="#0000FF">
|
<body bgcolor="white" text="black" link="#0000FF" vlink="#840084" alink="#0000FF">
|
||||||
@ -20,7 +20,7 @@
|
|||||||
</tr></table>
|
</tr></table>
|
||||||
<hr>
|
<hr>
|
||||||
<div class="spirit-nav">
|
<div class="spirit-nav">
|
||||||
<a accesskey="p" href="in_place_factories.html"><img src="../../../../../doc/src/images/prev.png" alt="Prev"></a><a accesskey="u" href="../index.html"><img src="../../../../../doc/src/images/up.png" alt="Up"></a><a accesskey="h" href="../index.html"><img src="../../../../../doc/src/images/home.png" alt="Home"></a><a accesskey="n" href="exception_safety_guarantees.html"><img src="../../../../../doc/src/images/next.png" alt="Next"></a>
|
<a accesskey="p" href="detailed_semantics.html"><img src="../../../../../doc/src/images/prev.png" alt="Prev"></a><a accesskey="u" href="../index.html"><img src="../../../../../doc/src/images/up.png" alt="Up"></a><a accesskey="h" href="../index.html"><img src="../../../../../doc/src/images/home.png" alt="Home"></a><a accesskey="n" href="exception_safety_guarantees.html"><img src="../../../../../doc/src/images/next.png" alt="Next"></a>
|
||||||
</div>
|
</div>
|
||||||
<div class="section">
|
<div class="section">
|
||||||
<div class="titlepage"><div><div><h2 class="title" style="clear: both">
|
<div class="titlepage"><div><div><h2 class="title" style="clear: both">
|
||||||
@ -102,7 +102,7 @@
|
|||||||
</tr></table>
|
</tr></table>
|
||||||
<hr>
|
<hr>
|
||||||
<div class="spirit-nav">
|
<div class="spirit-nav">
|
||||||
<a accesskey="p" href="in_place_factories.html"><img src="../../../../../doc/src/images/prev.png" alt="Prev"></a><a accesskey="u" href="../index.html"><img src="../../../../../doc/src/images/up.png" alt="Up"></a><a accesskey="h" href="../index.html"><img src="../../../../../doc/src/images/home.png" alt="Home"></a><a accesskey="n" href="exception_safety_guarantees.html"><img src="../../../../../doc/src/images/next.png" alt="Next"></a>
|
<a accesskey="p" href="detailed_semantics.html"><img src="../../../../../doc/src/images/prev.png" alt="Prev"></a><a accesskey="u" href="../index.html"><img src="../../../../../doc/src/images/up.png" alt="Up"></a><a accesskey="h" href="../index.html"><img src="../../../../../doc/src/images/home.png" alt="Home"></a><a accesskey="n" href="exception_safety_guarantees.html"><img src="../../../../../doc/src/images/next.png" alt="Next"></a>
|
||||||
</div>
|
</div>
|
||||||
</body>
|
</body>
|
||||||
</html>
|
</html>
|
||||||
|
@ -6,7 +6,7 @@
|
|||||||
<meta name="generator" content="DocBook XSL Stylesheets V1.78.1">
|
<meta name="generator" content="DocBook XSL Stylesheets V1.78.1">
|
||||||
<link rel="home" href="../index.html" title="Chapter 1. Boost.Optional">
|
<link rel="home" href="../index.html" title="Chapter 1. Boost.Optional">
|
||||||
<link rel="up" href="../index.html" title="Chapter 1. Boost.Optional">
|
<link rel="up" href="../index.html" title="Chapter 1. Boost.Optional">
|
||||||
<link rel="prev" href="dependencies_and_portability.html" title="Dependencies and Portability">
|
<link rel="prev" href="dependencies_and_portability/optional_reference_binding.html" title="Optional Reference Binding">
|
||||||
</head>
|
</head>
|
||||||
<body bgcolor="white" text="black" link="#0000FF" vlink="#840084" alink="#0000FF">
|
<body bgcolor="white" text="black" link="#0000FF" vlink="#840084" alink="#0000FF">
|
||||||
<table cellpadding="2" width="100%"><tr>
|
<table cellpadding="2" width="100%"><tr>
|
||||||
@ -19,7 +19,7 @@
|
|||||||
</tr></table>
|
</tr></table>
|
||||||
<hr>
|
<hr>
|
||||||
<div class="spirit-nav">
|
<div class="spirit-nav">
|
||||||
<a accesskey="p" href="dependencies_and_portability.html"><img src="../../../../../doc/src/images/prev.png" alt="Prev"></a><a accesskey="u" href="../index.html"><img src="../../../../../doc/src/images/up.png" alt="Up"></a><a accesskey="h" href="../index.html"><img src="../../../../../doc/src/images/home.png" alt="Home"></a>
|
<a accesskey="p" href="dependencies_and_portability/optional_reference_binding.html"><img src="../../../../../doc/src/images/prev.png" alt="Prev"></a><a accesskey="u" href="../index.html"><img src="../../../../../doc/src/images/up.png" alt="Up"></a><a accesskey="h" href="../index.html"><img src="../../../../../doc/src/images/home.png" alt="Home"></a>
|
||||||
</div>
|
</div>
|
||||||
<div class="section">
|
<div class="section">
|
||||||
<div class="titlepage"><div><div><h2 class="title" style="clear: both">
|
<div class="titlepage"><div><div><h2 class="title" style="clear: both">
|
||||||
@ -119,7 +119,7 @@
|
|||||||
</tr></table>
|
</tr></table>
|
||||||
<hr>
|
<hr>
|
||||||
<div class="spirit-nav">
|
<div class="spirit-nav">
|
||||||
<a accesskey="p" href="dependencies_and_portability.html"><img src="../../../../../doc/src/images/prev.png" alt="Prev"></a><a accesskey="u" href="../index.html"><img src="../../../../../doc/src/images/up.png" alt="Up"></a><a accesskey="h" href="../index.html"><img src="../../../../../doc/src/images/home.png" alt="Home"></a>
|
<a accesskey="p" href="dependencies_and_portability/optional_reference_binding.html"><img src="../../../../../doc/src/images/prev.png" alt="Prev"></a><a accesskey="u" href="../index.html"><img src="../../../../../doc/src/images/up.png" alt="Up"></a><a accesskey="h" href="../index.html"><img src="../../../../../doc/src/images/home.png" alt="Home"></a>
|
||||||
</div>
|
</div>
|
||||||
</body>
|
</body>
|
||||||
</html>
|
</html>
|
||||||
|
@ -6,8 +6,8 @@
|
|||||||
<meta name="generator" content="DocBook XSL Stylesheets V1.78.1">
|
<meta name="generator" content="DocBook XSL Stylesheets V1.78.1">
|
||||||
<link rel="home" href="../index.html" title="Chapter 1. Boost.Optional">
|
<link rel="home" href="../index.html" title="Chapter 1. Boost.Optional">
|
||||||
<link rel="up" href="../index.html" title="Chapter 1. Boost.Optional">
|
<link rel="up" href="../index.html" title="Chapter 1. Boost.Optional">
|
||||||
<link rel="prev" href="type_requirements.html" title="Type requirements">
|
<link rel="prev" href="reference/detailed_semantics.html" title="Detailed Semantics">
|
||||||
<link rel="next" href="acknowledgments.html" title="Acknowledgments">
|
<link rel="next" href="dependencies_and_portability/optional_reference_binding.html" title="Optional Reference Binding">
|
||||||
</head>
|
</head>
|
||||||
<body bgcolor="white" text="black" link="#0000FF" vlink="#840084" alink="#0000FF">
|
<body bgcolor="white" text="black" link="#0000FF" vlink="#840084" alink="#0000FF">
|
||||||
<table cellpadding="2" width="100%"><tr>
|
<table cellpadding="2" width="100%"><tr>
|
||||||
@ -20,81 +20,19 @@
|
|||||||
</tr></table>
|
</tr></table>
|
||||||
<hr>
|
<hr>
|
||||||
<div class="spirit-nav">
|
<div class="spirit-nav">
|
||||||
<a accesskey="p" href="type_requirements.html"><img src="../../../../../doc/src/images/prev.png" alt="Prev"></a><a accesskey="u" href="../index.html"><img src="../../../../../doc/src/images/up.png" alt="Up"></a><a accesskey="h" href="../index.html"><img src="../../../../../doc/src/images/home.png" alt="Home"></a><a accesskey="n" href="acknowledgments.html"><img src="../../../../../doc/src/images/next.png" alt="Next"></a>
|
<a accesskey="p" href="reference/detailed_semantics.html"><img src="../../../../../doc/src/images/prev.png" alt="Prev"></a><a accesskey="u" href="../index.html"><img src="../../../../../doc/src/images/up.png" alt="Up"></a><a accesskey="h" href="../index.html"><img src="../../../../../doc/src/images/home.png" alt="Home"></a><a accesskey="n" href="dependencies_and_portability/optional_reference_binding.html"><img src="../../../../../doc/src/images/next.png" alt="Next"></a>
|
||||||
</div>
|
</div>
|
||||||
<div class="section">
|
<div class="section">
|
||||||
<div class="titlepage"><div><div><h2 class="title" style="clear: both">
|
<div class="titlepage"><div><div><h2 class="title" style="clear: both">
|
||||||
<a name="boost_optional.dependencies_and_portability"></a><a class="link" href="dependencies_and_portability.html" title="Dependencies and Portability">Dependencies
|
<a name="boost_optional.dependencies_and_portability"></a><a class="link" href="dependencies_and_portability.html" title="Dependencies and Portability">Dependencies
|
||||||
and Portability</a>
|
and Portability</a>
|
||||||
</h2></div></div></div>
|
</h2></div></div></div>
|
||||||
<div class="toc"><dl class="toc"><dt><span class="section"><a href="dependencies_and_portability.html#boost_optional.dependencies_and_portability.optional_reference_binding">Optional
|
<div class="toc"><dl class="toc"><dt><span class="section"><a href="dependencies_and_portability/optional_reference_binding.html">Optional
|
||||||
Reference Binding</a></span></dt></dl></div>
|
Reference Binding</a></span></dt></dl></div>
|
||||||
<p>
|
<p>
|
||||||
The implementation uses <code class="computeroutput"><span class="identifier">type_traits</span><span class="special">/</span><span class="identifier">alignment_of</span><span class="special">.</span><span class="identifier">hpp</span></code> and
|
The implementation uses <code class="computeroutput"><span class="identifier">type_traits</span><span class="special">/</span><span class="identifier">alignment_of</span><span class="special">.</span><span class="identifier">hpp</span></code> and
|
||||||
<code class="computeroutput"><span class="identifier">type_traits</span><span class="special">/</span><span class="identifier">type_with_alignment</span><span class="special">.</span><span class="identifier">hpp</span></code>
|
<code class="computeroutput"><span class="identifier">type_traits</span><span class="special">/</span><span class="identifier">type_with_alignment</span><span class="special">.</span><span class="identifier">hpp</span></code>
|
||||||
</p>
|
</p>
|
||||||
<div class="section">
|
|
||||||
<div class="titlepage"><div><div><h3 class="title">
|
|
||||||
<a name="boost_optional.dependencies_and_portability.optional_reference_binding"></a><a class="link" href="dependencies_and_portability.html#boost_optional.dependencies_and_portability.optional_reference_binding" title="Optional Reference Binding">Optional
|
|
||||||
Reference Binding</a>
|
|
||||||
</h3></div></div></div>
|
|
||||||
<p>
|
|
||||||
On compilers that do not conform to Standard C++ rules of reference binding,
|
|
||||||
operations on optional references might give adverse results: rather than
|
|
||||||
binding a reference to a designated object they may create an unexpected
|
|
||||||
temporary and bind to it. Compilers known to have these deficiencies include
|
|
||||||
GCC versions 4.2, 4.3, 4.4, 4.5; QCC 4.4.2; MSVC versions 8.0, 9.0, 10.0,
|
|
||||||
11.0, 12.0. On these compilers prefer using direct-initialization and copy
|
|
||||||
assignment of optional references to copy-initialization and assignment from
|
|
||||||
<code class="computeroutput"><span class="identifier">T</span><span class="special">&</span></code>:
|
|
||||||
</p>
|
|
||||||
<pre class="programlisting"><span class="keyword">const</span> <span class="keyword">int</span> <span class="identifier">i</span> <span class="special">=</span> <span class="number">0</span><span class="special">;</span>
|
|
||||||
<span class="identifier">optional</span><span class="special"><</span><span class="keyword">const</span> <span class="keyword">int</span><span class="special">&></span> <span class="identifier">or1</span><span class="special">;</span>
|
|
||||||
<span class="identifier">optional</span><span class="special"><</span><span class="keyword">const</span> <span class="keyword">int</span><span class="special">&></span> <span class="identifier">or2</span> <span class="special">=</span> <span class="identifier">i</span><span class="special">;</span> <span class="comment">// not portable</span>
|
|
||||||
<span class="identifier">or1</span> <span class="special">=</span> <span class="identifier">i</span><span class="special">;</span> <span class="comment">// not portable</span>
|
|
||||||
|
|
||||||
<span class="identifier">optional</span><span class="special"><</span><span class="keyword">const</span> <span class="keyword">int</span><span class="special">&></span> <span class="identifier">or3</span><span class="special">(</span><span class="identifier">i</span><span class="special">);</span> <span class="comment">// portable</span>
|
|
||||||
<span class="identifier">or1</span> <span class="special">=</span> <span class="identifier">optional</span><span class="special"><</span><span class="keyword">const</span> <span class="keyword">int</span><span class="special">&>(</span><span class="identifier">i</span><span class="special">);</span> <span class="comment">// portable</span>
|
|
||||||
</pre>
|
|
||||||
<p>
|
|
||||||
In order to check if your compiler correctly implements reference binding
|
|
||||||
use this test program.
|
|
||||||
</p>
|
|
||||||
<pre class="programlisting"><span class="preprocessor">#include</span> <span class="special"><</span><span class="identifier">cassert</span><span class="special">></span>
|
|
||||||
|
|
||||||
<span class="keyword">const</span> <span class="keyword">int</span> <span class="identifier">global_i</span> <span class="special">=</span> <span class="number">0</span><span class="special">;</span>
|
|
||||||
|
|
||||||
<span class="keyword">struct</span> <span class="identifier">TestingReferenceBinding</span>
|
|
||||||
<span class="special">{</span>
|
|
||||||
<span class="identifier">TestingReferenceBinding</span><span class="special">(</span><span class="keyword">const</span> <span class="keyword">int</span><span class="special">&</span> <span class="identifier">ii</span><span class="special">)</span>
|
|
||||||
<span class="special">{</span>
|
|
||||||
<span class="identifier">assert</span><span class="special">(&</span><span class="identifier">ii</span> <span class="special">==</span> <span class="special">&</span><span class="identifier">global_i</span><span class="special">);</span>
|
|
||||||
<span class="special">}</span>
|
|
||||||
|
|
||||||
<span class="keyword">void</span> <span class="keyword">operator</span><span class="special">=(</span><span class="keyword">const</span> <span class="keyword">int</span><span class="special">&</span> <span class="identifier">ii</span><span class="special">)</span>
|
|
||||||
<span class="special">{</span>
|
|
||||||
<span class="identifier">assert</span><span class="special">(&</span><span class="identifier">ii</span> <span class="special">==</span> <span class="special">&</span><span class="identifier">global_i</span><span class="special">);</span>
|
|
||||||
<span class="special">}</span>
|
|
||||||
|
|
||||||
<span class="keyword">void</span> <span class="keyword">operator</span><span class="special">=(</span><span class="keyword">int</span><span class="special">&&)</span> <span class="comment">// remove this if your compiler doesn't have rvalue refs</span>
|
|
||||||
<span class="special">{</span>
|
|
||||||
<span class="identifier">assert</span><span class="special">(</span><span class="keyword">false</span><span class="special">);</span>
|
|
||||||
<span class="special">}</span>
|
|
||||||
<span class="special">};</span>
|
|
||||||
|
|
||||||
<span class="keyword">int</span> <span class="identifier">main</span><span class="special">()</span>
|
|
||||||
<span class="special">{</span>
|
|
||||||
<span class="keyword">const</span> <span class="keyword">int</span><span class="special">&</span> <span class="identifier">iref</span> <span class="special">=</span> <span class="identifier">global_i</span><span class="special">;</span>
|
|
||||||
<span class="identifier">assert</span><span class="special">(&</span><span class="identifier">iref</span> <span class="special">==</span> <span class="special">&</span><span class="identifier">global_i</span><span class="special">);</span>
|
|
||||||
|
|
||||||
<span class="identifier">TestingReferenceBinding</span> <span class="identifier">ttt</span> <span class="special">=</span> <span class="identifier">global_i</span><span class="special">;</span>
|
|
||||||
<span class="identifier">ttt</span> <span class="special">=</span> <span class="identifier">global_i</span><span class="special">;</span>
|
|
||||||
|
|
||||||
<span class="identifier">TestingReferenceBinding</span> <span class="identifier">ttt2</span> <span class="special">=</span> <span class="identifier">iref</span><span class="special">;</span>
|
|
||||||
<span class="identifier">ttt2</span> <span class="special">=</span> <span class="identifier">iref</span><span class="special">;</span>
|
|
||||||
<span class="special">}</span>
|
|
||||||
</pre>
|
|
||||||
</div>
|
|
||||||
</div>
|
</div>
|
||||||
<table xmlns:rev="http://www.cs.rpi.edu/~gregod/boost/tools/doc/revision" width="100%"><tr>
|
<table xmlns:rev="http://www.cs.rpi.edu/~gregod/boost/tools/doc/revision" width="100%"><tr>
|
||||||
<td align="left"></td>
|
<td align="left"></td>
|
||||||
@ -106,7 +44,7 @@
|
|||||||
</tr></table>
|
</tr></table>
|
||||||
<hr>
|
<hr>
|
||||||
<div class="spirit-nav">
|
<div class="spirit-nav">
|
||||||
<a accesskey="p" href="type_requirements.html"><img src="../../../../../doc/src/images/prev.png" alt="Prev"></a><a accesskey="u" href="../index.html"><img src="../../../../../doc/src/images/up.png" alt="Up"></a><a accesskey="h" href="../index.html"><img src="../../../../../doc/src/images/home.png" alt="Home"></a><a accesskey="n" href="acknowledgments.html"><img src="../../../../../doc/src/images/next.png" alt="Next"></a>
|
<a accesskey="p" href="reference/detailed_semantics.html"><img src="../../../../../doc/src/images/prev.png" alt="Prev"></a><a accesskey="u" href="../index.html"><img src="../../../../../doc/src/images/up.png" alt="Up"></a><a accesskey="h" href="../index.html"><img src="../../../../../doc/src/images/home.png" alt="Home"></a><a accesskey="n" href="dependencies_and_portability/optional_reference_binding.html"><img src="../../../../../doc/src/images/next.png" alt="Next"></a>
|
||||||
</div>
|
</div>
|
||||||
</body>
|
</body>
|
||||||
</html>
|
</html>
|
||||||
|
@ -0,0 +1,100 @@
|
|||||||
|
<html>
|
||||||
|
<head>
|
||||||
|
<meta http-equiv="Content-Type" content="text/html; charset=US-ASCII">
|
||||||
|
<title>Optional Reference Binding</title>
|
||||||
|
<link rel="stylesheet" href="../../../../../../doc/src/boostbook.css" type="text/css">
|
||||||
|
<meta name="generator" content="DocBook XSL Stylesheets V1.78.1">
|
||||||
|
<link rel="home" href="../../index.html" title="Chapter 1. Boost.Optional">
|
||||||
|
<link rel="up" href="../dependencies_and_portability.html" title="Dependencies and Portability">
|
||||||
|
<link rel="prev" href="../dependencies_and_portability.html" title="Dependencies and Portability">
|
||||||
|
<link rel="next" href="../acknowledgments.html" title="Acknowledgments">
|
||||||
|
</head>
|
||||||
|
<body bgcolor="white" text="black" link="#0000FF" vlink="#840084" alink="#0000FF">
|
||||||
|
<table cellpadding="2" width="100%"><tr>
|
||||||
|
<td valign="top"><img alt="Boost C++ Libraries" width="277" height="86" src="../../../../../../boost.png"></td>
|
||||||
|
<td align="center"><a href="../../../../../../index.html">Home</a></td>
|
||||||
|
<td align="center"><a href="../../../../../../libs/libraries.htm">Libraries</a></td>
|
||||||
|
<td align="center"><a href="http://www.boost.org/users/people.html">People</a></td>
|
||||||
|
<td align="center"><a href="http://www.boost.org/users/faq.html">FAQ</a></td>
|
||||||
|
<td align="center"><a href="../../../../../../more/index.htm">More</a></td>
|
||||||
|
</tr></table>
|
||||||
|
<hr>
|
||||||
|
<div class="spirit-nav">
|
||||||
|
<a accesskey="p" href="../dependencies_and_portability.html"><img src="../../../../../../doc/src/images/prev.png" alt="Prev"></a><a accesskey="u" href="../dependencies_and_portability.html"><img src="../../../../../../doc/src/images/up.png" alt="Up"></a><a accesskey="h" href="../../index.html"><img src="../../../../../../doc/src/images/home.png" alt="Home"></a><a accesskey="n" href="../acknowledgments.html"><img src="../../../../../../doc/src/images/next.png" alt="Next"></a>
|
||||||
|
</div>
|
||||||
|
<div class="section">
|
||||||
|
<div class="titlepage"><div><div><h3 class="title">
|
||||||
|
<a name="boost_optional.dependencies_and_portability.optional_reference_binding"></a><a class="link" href="optional_reference_binding.html" title="Optional Reference Binding">Optional
|
||||||
|
Reference Binding</a>
|
||||||
|
</h3></div></div></div>
|
||||||
|
<p>
|
||||||
|
On compilers that do not conform to Standard C++ rules of reference binding,
|
||||||
|
operations on optional references might give adverse results: rather than
|
||||||
|
binding a reference to a designated object they may create an unexpected
|
||||||
|
temporary and bind to it. Compilers known to have these deficiencies include
|
||||||
|
GCC versions 4.2, 4.3, 4.4, 4.5; QCC 4.4.2; MSVC versions 8.0, 9.0, 10.0,
|
||||||
|
11.0, 12.0. On these compilers prefer using direct-initialization and copy
|
||||||
|
assignment of optional references to copy-initialization and assignment from
|
||||||
|
<code class="computeroutput"><span class="identifier">T</span><span class="special">&</span></code>:
|
||||||
|
</p>
|
||||||
|
<pre class="programlisting"><span class="keyword">const</span> <span class="keyword">int</span> <span class="identifier">i</span> <span class="special">=</span> <span class="number">0</span><span class="special">;</span>
|
||||||
|
<span class="identifier">optional</span><span class="special"><</span><span class="keyword">const</span> <span class="keyword">int</span><span class="special">&></span> <span class="identifier">or1</span><span class="special">;</span>
|
||||||
|
<span class="identifier">optional</span><span class="special"><</span><span class="keyword">const</span> <span class="keyword">int</span><span class="special">&></span> <span class="identifier">or2</span> <span class="special">=</span> <span class="identifier">i</span><span class="special">;</span> <span class="comment">// not portable</span>
|
||||||
|
<span class="identifier">or1</span> <span class="special">=</span> <span class="identifier">i</span><span class="special">;</span> <span class="comment">// not portable</span>
|
||||||
|
|
||||||
|
<span class="identifier">optional</span><span class="special"><</span><span class="keyword">const</span> <span class="keyword">int</span><span class="special">&></span> <span class="identifier">or3</span><span class="special">(</span><span class="identifier">i</span><span class="special">);</span> <span class="comment">// portable</span>
|
||||||
|
<span class="identifier">or1</span> <span class="special">=</span> <span class="identifier">optional</span><span class="special"><</span><span class="keyword">const</span> <span class="keyword">int</span><span class="special">&>(</span><span class="identifier">i</span><span class="special">);</span> <span class="comment">// portable</span>
|
||||||
|
</pre>
|
||||||
|
<p>
|
||||||
|
In order to check if your compiler correctly implements reference binding
|
||||||
|
use this test program.
|
||||||
|
</p>
|
||||||
|
<pre class="programlisting"><span class="preprocessor">#include</span> <span class="special"><</span><span class="identifier">cassert</span><span class="special">></span>
|
||||||
|
|
||||||
|
<span class="keyword">const</span> <span class="keyword">int</span> <span class="identifier">global_i</span> <span class="special">=</span> <span class="number">0</span><span class="special">;</span>
|
||||||
|
|
||||||
|
<span class="keyword">struct</span> <span class="identifier">TestingReferenceBinding</span>
|
||||||
|
<span class="special">{</span>
|
||||||
|
<span class="identifier">TestingReferenceBinding</span><span class="special">(</span><span class="keyword">const</span> <span class="keyword">int</span><span class="special">&</span> <span class="identifier">ii</span><span class="special">)</span>
|
||||||
|
<span class="special">{</span>
|
||||||
|
<span class="identifier">assert</span><span class="special">(&</span><span class="identifier">ii</span> <span class="special">==</span> <span class="special">&</span><span class="identifier">global_i</span><span class="special">);</span>
|
||||||
|
<span class="special">}</span>
|
||||||
|
|
||||||
|
<span class="keyword">void</span> <span class="keyword">operator</span><span class="special">=(</span><span class="keyword">const</span> <span class="keyword">int</span><span class="special">&</span> <span class="identifier">ii</span><span class="special">)</span>
|
||||||
|
<span class="special">{</span>
|
||||||
|
<span class="identifier">assert</span><span class="special">(&</span><span class="identifier">ii</span> <span class="special">==</span> <span class="special">&</span><span class="identifier">global_i</span><span class="special">);</span>
|
||||||
|
<span class="special">}</span>
|
||||||
|
|
||||||
|
<span class="keyword">void</span> <span class="keyword">operator</span><span class="special">=(</span><span class="keyword">int</span><span class="special">&&)</span> <span class="comment">// remove this if your compiler doesn't have rvalue refs</span>
|
||||||
|
<span class="special">{</span>
|
||||||
|
<span class="identifier">assert</span><span class="special">(</span><span class="keyword">false</span><span class="special">);</span>
|
||||||
|
<span class="special">}</span>
|
||||||
|
<span class="special">};</span>
|
||||||
|
|
||||||
|
<span class="keyword">int</span> <span class="identifier">main</span><span class="special">()</span>
|
||||||
|
<span class="special">{</span>
|
||||||
|
<span class="keyword">const</span> <span class="keyword">int</span><span class="special">&</span> <span class="identifier">iref</span> <span class="special">=</span> <span class="identifier">global_i</span><span class="special">;</span>
|
||||||
|
<span class="identifier">assert</span><span class="special">(&</span><span class="identifier">iref</span> <span class="special">==</span> <span class="special">&</span><span class="identifier">global_i</span><span class="special">);</span>
|
||||||
|
|
||||||
|
<span class="identifier">TestingReferenceBinding</span> <span class="identifier">ttt</span> <span class="special">=</span> <span class="identifier">global_i</span><span class="special">;</span>
|
||||||
|
<span class="identifier">ttt</span> <span class="special">=</span> <span class="identifier">global_i</span><span class="special">;</span>
|
||||||
|
|
||||||
|
<span class="identifier">TestingReferenceBinding</span> <span class="identifier">ttt2</span> <span class="special">=</span> <span class="identifier">iref</span><span class="special">;</span>
|
||||||
|
<span class="identifier">ttt2</span> <span class="special">=</span> <span class="identifier">iref</span><span class="special">;</span>
|
||||||
|
<span class="special">}</span>
|
||||||
|
</pre>
|
||||||
|
</div>
|
||||||
|
<table xmlns:rev="http://www.cs.rpi.edu/~gregod/boost/tools/doc/revision" width="100%"><tr>
|
||||||
|
<td align="left"></td>
|
||||||
|
<td align="right"><div class="copyright-footer">Copyright © 2003-2007 Fernando Luis Cacciola Carballal<br>Copyright © 2014 Andrzej Krzemieński<p>
|
||||||
|
Distributed under the Boost Software License, Version 1.0. (See accompanying
|
||||||
|
file LICENSE_1_0.txt or copy at <a href="http://www.boost.org/LICENSE_1_0.txt" target="_top">http://www.boost.org/LICENSE_1_0.txt</a>)
|
||||||
|
</p>
|
||||||
|
</div></td>
|
||||||
|
</tr></table>
|
||||||
|
<hr>
|
||||||
|
<div class="spirit-nav">
|
||||||
|
<a accesskey="p" href="../dependencies_and_portability.html"><img src="../../../../../../doc/src/images/prev.png" alt="Prev"></a><a accesskey="u" href="../dependencies_and_portability.html"><img src="../../../../../../doc/src/images/up.png" alt="Up"></a><a accesskey="h" href="../../index.html"><img src="../../../../../../doc/src/images/home.png" alt="Home"></a><a accesskey="n" href="../acknowledgments.html"><img src="../../../../../../doc/src/images/next.png" alt="Next"></a>
|
||||||
|
</div>
|
||||||
|
</body>
|
||||||
|
</html>
|
@ -7,7 +7,7 @@
|
|||||||
<link rel="home" href="../index.html" title="Chapter 1. Boost.Optional">
|
<link rel="home" href="../index.html" title="Chapter 1. Boost.Optional">
|
||||||
<link rel="up" href="../index.html" title="Chapter 1. Boost.Optional">
|
<link rel="up" href="../index.html" title="Chapter 1. Boost.Optional">
|
||||||
<link rel="prev" href="synopsis.html" title="Synopsis">
|
<link rel="prev" href="synopsis.html" title="Synopsis">
|
||||||
<link rel="next" href="examples.html" title="Examples">
|
<link rel="next" href="dependencies_and_portability.html" title="Dependencies and Portability">
|
||||||
</head>
|
</head>
|
||||||
<body bgcolor="white" text="black" link="#0000FF" vlink="#840084" alink="#0000FF">
|
<body bgcolor="white" text="black" link="#0000FF" vlink="#840084" alink="#0000FF">
|
||||||
<table cellpadding="2" width="100%"><tr>
|
<table cellpadding="2" width="100%"><tr>
|
||||||
@ -20,7 +20,7 @@
|
|||||||
</tr></table>
|
</tr></table>
|
||||||
<hr>
|
<hr>
|
||||||
<div class="spirit-nav">
|
<div class="spirit-nav">
|
||||||
<a accesskey="p" href="synopsis.html"><img src="../../../../../doc/src/images/prev.png" alt="Prev"></a><a accesskey="u" href="../index.html"><img src="../../../../../doc/src/images/up.png" alt="Up"></a><a accesskey="h" href="../index.html"><img src="../../../../../doc/src/images/home.png" alt="Home"></a><a accesskey="n" href="examples.html"><img src="../../../../../doc/src/images/next.png" alt="Next"></a>
|
<a accesskey="p" href="synopsis.html"><img src="../../../../../doc/src/images/prev.png" alt="Prev"></a><a accesskey="u" href="../index.html"><img src="../../../../../doc/src/images/up.png" alt="Up"></a><a accesskey="h" href="../index.html"><img src="../../../../../doc/src/images/home.png" alt="Home"></a><a accesskey="n" href="dependencies_and_portability.html"><img src="../../../../../doc/src/images/next.png" alt="Next"></a>
|
||||||
</div>
|
</div>
|
||||||
<div class="section">
|
<div class="section">
|
||||||
<div class="titlepage"><div><div><h2 class="title" style="clear: both">
|
<div class="titlepage"><div><div><h2 class="title" style="clear: both">
|
||||||
@ -606,7 +606,7 @@
|
|||||||
constructor called by the factory throws.
|
constructor called by the factory throws.
|
||||||
</li>
|
</li>
|
||||||
<li class="listitem">
|
<li class="listitem">
|
||||||
<span class="bold"><strong>Notes:</strong></span> See <a class="link" href="in_place_factories.html" title="In-Place Factories">In-Place
|
<span class="bold"><strong>Notes:</strong></span> See <a class="link" href="tutorial/in_place_factories.html" title="In-Place Factories">In-Place
|
||||||
Factories</a>
|
Factories</a>
|
||||||
</li>
|
</li>
|
||||||
<li class="listitem">
|
<li class="listitem">
|
||||||
@ -712,7 +712,7 @@
|
|||||||
</li>
|
</li>
|
||||||
<li class="listitem">
|
<li class="listitem">
|
||||||
<span class="bold"><strong>Notes:</strong></span> If <code class="computeroutput"><span class="special">*</span><span class="keyword">this</span></code> was initialized, it is <span class="emphasis"><em>rebound</em></span>
|
<span class="bold"><strong>Notes:</strong></span> If <code class="computeroutput"><span class="special">*</span><span class="keyword">this</span></code> was initialized, it is <span class="emphasis"><em>rebound</em></span>
|
||||||
to the new object. See <a class="link" href="rebinding_semantics_for_assignment_of_optional_references.html" title="Rebinding semantics for assignment of optional references">here</a>
|
to the new object. See <a class="link" href="tutorial/rebinding_semantics_for_assignment_of_optional_references.html" title="Rebinding semantics for assignment of optional references">here</a>
|
||||||
for details on this behavior.
|
for details on this behavior.
|
||||||
</li>
|
</li>
|
||||||
<li class="listitem">
|
<li class="listitem">
|
||||||
@ -872,7 +872,7 @@
|
|||||||
<li class="listitem">
|
<li class="listitem">
|
||||||
<span class="bold"><strong>Notes:</strong></span> If <code class="computeroutput"><span class="special">*</span><span class="keyword">this</span></code> was initialized and so is <code class="computeroutput"><span class="special">*</span><span class="identifier">rhs</span></code>,
|
<span class="bold"><strong>Notes:</strong></span> If <code class="computeroutput"><span class="special">*</span><span class="keyword">this</span></code> was initialized and so is <code class="computeroutput"><span class="special">*</span><span class="identifier">rhs</span></code>,
|
||||||
<code class="computeroutput"><span class="special">*</span><span class="keyword">this</span></code>
|
<code class="computeroutput"><span class="special">*</span><span class="keyword">this</span></code>
|
||||||
is <span class="emphasis"><em>rebound</em></span> to the new object. See <a class="link" href="rebinding_semantics_for_assignment_of_optional_references.html" title="Rebinding semantics for assignment of optional references">here</a>
|
is <span class="emphasis"><em>rebound</em></span> to the new object. See <a class="link" href="tutorial/rebinding_semantics_for_assignment_of_optional_references.html" title="Rebinding semantics for assignment of optional references">here</a>
|
||||||
for details on this behavior.
|
for details on this behavior.
|
||||||
</li>
|
</li>
|
||||||
<li class="listitem">
|
<li class="listitem">
|
||||||
@ -1147,7 +1147,7 @@
|
|||||||
constructor called by the factory throws.
|
constructor called by the factory throws.
|
||||||
</li>
|
</li>
|
||||||
<li class="listitem">
|
<li class="listitem">
|
||||||
<span class="bold"><strong>Notes:</strong></span> See <a class="link" href="in_place_factories.html" title="In-Place Factories">In-Place
|
<span class="bold"><strong>Notes:</strong></span> See <a class="link" href="tutorial/in_place_factories.html" title="In-Place Factories">In-Place
|
||||||
Factories</a>
|
Factories</a>
|
||||||
</li>
|
</li>
|
||||||
<li class="listitem">
|
<li class="listitem">
|
||||||
@ -1177,20 +1177,12 @@
|
|||||||
<code class="computeroutput"><span class="keyword">void</span> <span class="identifier">optional</span><span class="special"><</span><span class="identifier">T</span><span class="special">>::</span><span class="identifier">reset</span><span class="special">()</span> <span class="keyword">noexcept</span> <span class="special">;</span></code>
|
<code class="computeroutput"><span class="keyword">void</span> <span class="identifier">optional</span><span class="special"><</span><span class="identifier">T</span><span class="special">>::</span><span class="identifier">reset</span><span class="special">()</span> <span class="keyword">noexcept</span> <span class="special">;</span></code>
|
||||||
</p></blockquote></div>
|
</p></blockquote></div>
|
||||||
<div class="itemizedlist"><ul class="itemizedlist" style="list-style-type: disc; "><li class="listitem">
|
<div class="itemizedlist"><ul class="itemizedlist" style="list-style-type: disc; "><li class="listitem">
|
||||||
<span class="bold"><strong>Deprecated:</strong></span> Same as <code class="computeroutput"><span class="keyword">operator</span><span class="special">=(</span> <span class="identifier">detail</span><span class="special">::</span><span class="identifier">none_t</span> <span class="special">);</span></code>
|
<span class="bold"><strong>Deprecated:</strong></span> Same as <code class="computeroutput"><span class="keyword">operator</span><span class="special">=(</span> <span class="identifier">none_t</span> <span class="special">);</span></code>
|
||||||
</li></ul></div>
|
</li></ul></div>
|
||||||
<p>
|
<p>
|
||||||
<span class="inlinemediaobject"><img src="../images/space.png" alt="space"></span>
|
<span class="inlinemediaobject"><img src="../images/space.png" alt="space"></span>
|
||||||
</p>
|
</p>
|
||||||
<a name="reference_optional_get"></a><div class="blockquote"><blockquote class="blockquote"><p>
|
<a name="reference_optional_get"></a><div class="blockquote"><blockquote class="blockquote"><p>
|
||||||
<code class="computeroutput"><span class="identifier">T</span> <span class="keyword">const</span><span class="special">&</span> <span class="identifier">optional</span><span class="special"><</span><span class="identifier">T</span></code>
|
|
||||||
<span class="emphasis"><em>(not a ref)</em></span><code class="computeroutput"><span class="special">>::</span><span class="keyword">operator</span><span class="special">*()</span> <span class="keyword">const</span> <span class="special">;</span></code>
|
|
||||||
</p></blockquote></div>
|
|
||||||
<div class="blockquote"><blockquote class="blockquote"><p>
|
|
||||||
<code class="computeroutput"><span class="identifier">T</span><span class="special">&</span>
|
|
||||||
<span class="identifier">optional</span><span class="special"><</span><span class="identifier">T</span></code> <span class="emphasis"><em>(not a ref)</em></span><code class="computeroutput"><span class="special">>::</span><span class="keyword">operator</span><span class="special">*();</span></code>
|
|
||||||
</p></blockquote></div>
|
|
||||||
<div class="blockquote"><blockquote class="blockquote"><p>
|
|
||||||
<code class="computeroutput"><span class="identifier">T</span> <span class="keyword">const</span><span class="special">&</span> <span class="identifier">optional</span><span class="special"><</span><span class="identifier">T</span></code>
|
<code class="computeroutput"><span class="identifier">T</span> <span class="keyword">const</span><span class="special">&</span> <span class="identifier">optional</span><span class="special"><</span><span class="identifier">T</span></code>
|
||||||
<span class="emphasis"><em>(not a ref)</em></span><code class="computeroutput"><span class="special">>::</span><span class="identifier">get</span><span class="special">()</span> <span class="keyword">const</span> <span class="special">;</span></code>
|
<span class="emphasis"><em>(not a ref)</em></span><code class="computeroutput"><span class="special">>::</span><span class="identifier">get</span><span class="special">()</span> <span class="keyword">const</span> <span class="special">;</span></code>
|
||||||
</p></blockquote></div>
|
</p></blockquote></div>
|
||||||
@ -1224,6 +1216,76 @@
|
|||||||
<span class="bold"><strong>Notes:</strong></span> The requirement is asserted via
|
<span class="bold"><strong>Notes:</strong></span> The requirement is asserted via
|
||||||
<code class="computeroutput"><span class="identifier">BOOST_ASSERT</span><span class="special">()</span></code>.
|
<code class="computeroutput"><span class="identifier">BOOST_ASSERT</span><span class="special">()</span></code>.
|
||||||
</li>
|
</li>
|
||||||
|
</ul></div>
|
||||||
|
<p>
|
||||||
|
<span class="inlinemediaobject"><img src="../images/space.png" alt="space"></span>
|
||||||
|
</p>
|
||||||
|
<div class="blockquote"><blockquote class="blockquote"><p>
|
||||||
|
<code class="computeroutput"><span class="identifier">T</span> <span class="keyword">const</span><span class="special">&</span> <span class="identifier">optional</span><span class="special"><</span><span class="identifier">T</span><span class="special">&>::</span><span class="identifier">get</span><span class="special">()</span> <span class="keyword">const</span> <span class="special">;</span></code>
|
||||||
|
</p></blockquote></div>
|
||||||
|
<div class="blockquote"><blockquote class="blockquote"><p>
|
||||||
|
<code class="computeroutput"><span class="identifier">T</span><span class="special">&</span>
|
||||||
|
<span class="identifier">optional</span><span class="special"><</span><span class="identifier">T</span><span class="special">&>::</span><span class="identifier">get</span><span class="special">()</span> <span class="special">;</span></code>
|
||||||
|
</p></blockquote></div>
|
||||||
|
<div class="blockquote"><blockquote class="blockquote"><p>
|
||||||
|
<code class="computeroutput"><span class="keyword">inline</span> <span class="identifier">T</span>
|
||||||
|
<span class="keyword">const</span><span class="special">&</span>
|
||||||
|
<span class="identifier">get</span> <span class="special">(</span>
|
||||||
|
<span class="identifier">optional</span><span class="special"><</span><span class="identifier">T</span><span class="special">&></span> <span class="keyword">const</span><span class="special">&</span> <span class="special">)</span> <span class="special">;</span></code>
|
||||||
|
</p></blockquote></div>
|
||||||
|
<div class="blockquote"><blockquote class="blockquote"><p>
|
||||||
|
<code class="computeroutput"><span class="keyword">inline</span> <span class="identifier">T</span><span class="special">&</span> <span class="identifier">get</span> <span class="special">(</span> <span class="identifier">optional</span><span class="special"><</span><span class="identifier">T</span><span class="special">&></span>
|
||||||
|
<span class="special">&)</span> <span class="special">;</span></code>
|
||||||
|
</p></blockquote></div>
|
||||||
|
<div class="itemizedlist"><ul class="itemizedlist" style="list-style-type: disc; ">
|
||||||
|
<li class="listitem">
|
||||||
|
<span class="bold"><strong>Requires: </strong></span> <code class="computeroutput"><span class="special">*</span><span class="keyword">this</span></code> is initialized
|
||||||
|
</li>
|
||||||
|
<li class="listitem">
|
||||||
|
<span class="bold"><strong>Returns:</strong></span> <span class="underline">The</span>
|
||||||
|
reference contained.
|
||||||
|
</li>
|
||||||
|
<li class="listitem">
|
||||||
|
<span class="bold"><strong>Throws:</strong></span> Nothing.
|
||||||
|
</li>
|
||||||
|
<li class="listitem">
|
||||||
|
<span class="bold"><strong>Notes:</strong></span> The requirement is asserted via
|
||||||
|
<code class="computeroutput"><span class="identifier">BOOST_ASSERT</span><span class="special">()</span></code>.
|
||||||
|
</li>
|
||||||
|
</ul></div>
|
||||||
|
<p>
|
||||||
|
<span class="inlinemediaobject"><img src="../images/space.png" alt="space"></span>
|
||||||
|
</p>
|
||||||
|
<a name="reference_optional_operator_asterisk"></a><div class="blockquote"><blockquote class="blockquote"><p>
|
||||||
|
<code class="computeroutput"><span class="identifier">T</span> <span class="keyword">const</span><span class="special">&</span> <span class="identifier">optional</span><span class="special"><</span><span class="identifier">T</span></code>
|
||||||
|
<span class="emphasis"><em>(not a ref)</em></span><code class="computeroutput"><span class="special">>::</span><span class="keyword">operator</span><span class="special">*()</span> <span class="keyword">const</span><span class="special">&</span> <span class="special">;</span></code>
|
||||||
|
</p></blockquote></div>
|
||||||
|
<div class="blockquote"><blockquote class="blockquote"><p>
|
||||||
|
<code class="computeroutput"><span class="identifier">T</span><span class="special">&</span>
|
||||||
|
<span class="identifier">optional</span><span class="special"><</span><span class="identifier">T</span></code> <span class="emphasis"><em>(not a ref)</em></span><code class="computeroutput"><span class="special">>::</span><span class="keyword">operator</span><span class="special">*()</span> <span class="special">&;</span></code>
|
||||||
|
</p></blockquote></div>
|
||||||
|
<div class="blockquote"><blockquote class="blockquote"><p>
|
||||||
|
<code class="computeroutput"><span class="identifier">T</span><span class="special">&&</span>
|
||||||
|
<span class="identifier">optional</span><span class="special"><</span><span class="identifier">T</span></code> <span class="emphasis"><em>(not a ref)</em></span><code class="computeroutput"><span class="special">>::</span><span class="keyword">operator</span><span class="special">*()</span> <span class="special">&&;</span></code>
|
||||||
|
</p></blockquote></div>
|
||||||
|
<div class="itemizedlist"><ul class="itemizedlist" style="list-style-type: disc; ">
|
||||||
|
<li class="listitem">
|
||||||
|
<span class="bold"><strong>Requires:</strong></span> <code class="computeroutput"><span class="special">*</span><span class="keyword">this</span></code> is initialized
|
||||||
|
</li>
|
||||||
|
<li class="listitem">
|
||||||
|
<span class="bold"><strong>Returns:</strong></span> A reference to the contained
|
||||||
|
value
|
||||||
|
</li>
|
||||||
|
<li class="listitem">
|
||||||
|
<span class="bold"><strong>Throws:</strong></span> Nothing.
|
||||||
|
</li>
|
||||||
|
<li class="listitem">
|
||||||
|
<span class="bold"><strong>Notes:</strong></span> The requirement is asserted via
|
||||||
|
<code class="computeroutput"><span class="identifier">BOOST_ASSERT</span><span class="special">()</span></code>.
|
||||||
|
On compilers that do not support ref-qualifiers on member functions these
|
||||||
|
three overloads are replaced with the classical two: a <code class="computeroutput"><span class="keyword">const</span></code>
|
||||||
|
and non-<code class="computeroutput"><span class="keyword">const</span></code> member functions.
|
||||||
|
</li>
|
||||||
<li class="listitem">
|
<li class="listitem">
|
||||||
<span class="bold"><strong>Example:</strong></span>
|
<span class="bold"><strong>Example:</strong></span>
|
||||||
<pre class="programlisting"><span class="identifier">T</span> <span class="identifier">v</span> <span class="special">;</span>
|
<pre class="programlisting"><span class="identifier">T</span> <span class="identifier">v</span> <span class="special">;</span>
|
||||||
@ -1236,15 +1298,63 @@
|
|||||||
</pre>
|
</pre>
|
||||||
</li>
|
</li>
|
||||||
</ul></div>
|
</ul></div>
|
||||||
|
<p>
|
||||||
|
<span class="inlinemediaobject"><img src="../images/space.png" alt="space"></span>
|
||||||
|
</p>
|
||||||
|
<div class="blockquote"><blockquote class="blockquote"><p>
|
||||||
|
<code class="computeroutput"><span class="identifier">T</span> <span class="keyword">const</span><span class="special">&</span> <span class="identifier">optional</span><span class="special"><</span><span class="identifier">T</span><span class="special">&>::</span><span class="keyword">operator</span><span class="special">*()</span> <span class="keyword">const</span><span class="special">&</span> <span class="special">;</span></code>
|
||||||
|
</p></blockquote></div>
|
||||||
|
<div class="blockquote"><blockquote class="blockquote"><p>
|
||||||
|
<code class="computeroutput"><span class="identifier">T</span> <span class="special">&</span>
|
||||||
|
<span class="identifier">optional</span><span class="special"><</span><span class="identifier">T</span><span class="special">&>::</span><span class="keyword">operator</span><span class="special">*()</span> <span class="special">&</span> <span class="special">;</span></code>
|
||||||
|
</p></blockquote></div>
|
||||||
|
<div class="blockquote"><blockquote class="blockquote"><p>
|
||||||
|
<code class="computeroutput"><span class="identifier">T</span> <span class="special">&</span>
|
||||||
|
<span class="identifier">optional</span><span class="special"><</span><span class="identifier">T</span><span class="special">&>::</span><span class="keyword">operator</span><span class="special">*()</span> <span class="special">&&</span> <span class="special">;</span></code>
|
||||||
|
</p></blockquote></div>
|
||||||
|
<div class="itemizedlist"><ul class="itemizedlist" style="list-style-type: disc; ">
|
||||||
|
<li class="listitem">
|
||||||
|
<span class="bold"><strong>Requires: </strong></span> <code class="computeroutput"><span class="special">*</span><span class="keyword">this</span></code> is initialized
|
||||||
|
</li>
|
||||||
|
<li class="listitem">
|
||||||
|
<span class="bold"><strong>Returns:</strong></span> <span class="underline">The</span>
|
||||||
|
reference contained.
|
||||||
|
</li>
|
||||||
|
<li class="listitem">
|
||||||
|
<span class="bold"><strong>Throws:</strong></span> Nothing.
|
||||||
|
</li>
|
||||||
|
<li class="listitem">
|
||||||
|
<span class="bold"><strong>Notes:</strong></span> The requirement is asserted via
|
||||||
|
<code class="computeroutput"><span class="identifier">BOOST_ASSERT</span><span class="special">()</span></code>.
|
||||||
|
On compilers that do not support ref-qualifiers on member functions these
|
||||||
|
three overloads are replaced with the classical two: a <code class="computeroutput"><span class="keyword">const</span></code>
|
||||||
|
and non-<code class="computeroutput"><span class="keyword">const</span></code> member functions.
|
||||||
|
</li>
|
||||||
|
<li class="listitem">
|
||||||
|
<span class="bold"><strong>Example:</strong></span>
|
||||||
|
<pre class="programlisting"><span class="identifier">T</span> <span class="identifier">v</span> <span class="special">;</span>
|
||||||
|
<span class="identifier">T</span><span class="special">&</span> <span class="identifier">vref</span> <span class="special">=</span> <span class="identifier">v</span> <span class="special">;</span>
|
||||||
|
<span class="identifier">optional</span><span class="special"><</span><span class="identifier">T</span><span class="special">&></span> <span class="identifier">opt</span> <span class="special">(</span> <span class="identifier">vref</span> <span class="special">);</span>
|
||||||
|
<span class="identifier">T</span> <span class="keyword">const</span><span class="special">&</span> <span class="identifier">vref2</span> <span class="special">=</span> <span class="special">*</span><span class="identifier">opt</span><span class="special">;</span>
|
||||||
|
<span class="identifier">assert</span> <span class="special">(</span> <span class="identifier">vref2</span> <span class="special">==</span> <span class="identifier">v</span> <span class="special">)</span> <span class="special">;</span>
|
||||||
|
<span class="special">++</span> <span class="identifier">v</span> <span class="special">;</span>
|
||||||
|
<span class="identifier">assert</span> <span class="special">(</span> <span class="special">*</span><span class="identifier">opt</span> <span class="special">==</span> <span class="identifier">v</span> <span class="special">)</span> <span class="special">;</span>
|
||||||
|
</pre>
|
||||||
|
</li>
|
||||||
|
</ul></div>
|
||||||
<p>
|
<p>
|
||||||
<span class="inlinemediaobject"><img src="../images/space.png" alt="space"></span>
|
<span class="inlinemediaobject"><img src="../images/space.png" alt="space"></span>
|
||||||
</p>
|
</p>
|
||||||
<a name="reference_optional_value"></a><div class="blockquote"><blockquote class="blockquote"><p>
|
<a name="reference_optional_value"></a><div class="blockquote"><blockquote class="blockquote"><p>
|
||||||
<code class="computeroutput"><span class="identifier">T</span> <span class="keyword">const</span><span class="special">&</span> <span class="identifier">optional</span><span class="special"><</span><span class="identifier">T</span><span class="special">>::</span><span class="identifier">value</span><span class="special">()</span> <span class="keyword">const</span> <span class="special">;</span></code>
|
<code class="computeroutput"><span class="identifier">T</span> <span class="keyword">const</span><span class="special">&</span> <span class="identifier">optional</span><span class="special"><</span><span class="identifier">T</span><span class="special">>::</span><span class="identifier">value</span><span class="special">()</span> <span class="keyword">const</span><span class="special">&</span> <span class="special">;</span></code>
|
||||||
</p></blockquote></div>
|
</p></blockquote></div>
|
||||||
<div class="blockquote"><blockquote class="blockquote"><p>
|
<div class="blockquote"><blockquote class="blockquote"><p>
|
||||||
<code class="computeroutput"><span class="identifier">T</span><span class="special">&</span>
|
<code class="computeroutput"><span class="identifier">T</span><span class="special">&</span>
|
||||||
<span class="identifier">optional</span><span class="special"><</span><span class="identifier">T</span><span class="special">>::</span><span class="identifier">value</span><span class="special">();</span></code>
|
<span class="identifier">optional</span><span class="special"><</span><span class="identifier">T</span><span class="special">>::</span><span class="identifier">value</span><span class="special">()</span> <span class="special">&</span> <span class="special">;</span></code>
|
||||||
|
</p></blockquote></div>
|
||||||
|
<div class="blockquote"><blockquote class="blockquote"><p>
|
||||||
|
<code class="computeroutput"><span class="identifier">T</span><span class="special">&&</span>
|
||||||
|
<span class="identifier">optional</span><span class="special"><</span><span class="identifier">T</span><span class="special">>::</span><span class="identifier">value</span><span class="special">()</span> <span class="special">&&</span> <span class="special">;</span></code>
|
||||||
</p></blockquote></div>
|
</p></blockquote></div>
|
||||||
<div class="itemizedlist"><ul class="itemizedlist" style="list-style-type: disc; ">
|
<div class="itemizedlist"><ul class="itemizedlist" style="list-style-type: disc; ">
|
||||||
<li class="listitem">
|
<li class="listitem">
|
||||||
@ -1257,6 +1367,12 @@
|
|||||||
if <code class="computeroutput"><span class="special">*</span><span class="keyword">this</span></code>
|
if <code class="computeroutput"><span class="special">*</span><span class="keyword">this</span></code>
|
||||||
is not initialized.
|
is not initialized.
|
||||||
</li>
|
</li>
|
||||||
|
<li class="listitem">
|
||||||
|
<span class="bold"><strong>Notes:</strong></span> On compilers that do not support
|
||||||
|
ref-qualifiers on member functions these three overloads are replaced with
|
||||||
|
the classical two: a <code class="computeroutput"><span class="keyword">const</span></code>
|
||||||
|
and non-<code class="computeroutput"><span class="keyword">const</span></code> member functions.
|
||||||
|
</li>
|
||||||
<li class="listitem">
|
<li class="listitem">
|
||||||
<span class="bold"><strong>Example:</strong></span>
|
<span class="bold"><strong>Example:</strong></span>
|
||||||
<pre class="programlisting"><span class="identifier">T</span> <span class="identifier">v</span> <span class="special">;</span>
|
<pre class="programlisting"><span class="identifier">T</span> <span class="identifier">v</span> <span class="special">;</span>
|
||||||
@ -1276,7 +1392,11 @@
|
|||||||
</ul></div>
|
</ul></div>
|
||||||
<a name="reference_optional_value_or"></a><div class="blockquote"><blockquote class="blockquote"><p>
|
<a name="reference_optional_value_or"></a><div class="blockquote"><blockquote class="blockquote"><p>
|
||||||
<code class="computeroutput"><span class="keyword">template</span><span class="special"><</span><span class="keyword">class</span> <span class="identifier">U</span><span class="special">></span> <span class="identifier">T</span> <span class="identifier">optional</span><span class="special"><</span><span class="identifier">T</span><span class="special">>::</span><span class="identifier">value_or</span><span class="special">(</span><span class="identifier">U</span> <span class="special">&&</span>
|
<code class="computeroutput"><span class="keyword">template</span><span class="special"><</span><span class="keyword">class</span> <span class="identifier">U</span><span class="special">></span> <span class="identifier">T</span> <span class="identifier">optional</span><span class="special"><</span><span class="identifier">T</span><span class="special">>::</span><span class="identifier">value_or</span><span class="special">(</span><span class="identifier">U</span> <span class="special">&&</span>
|
||||||
<span class="identifier">v</span><span class="special">)</span> <span class="keyword">const</span> <span class="special">;</span></code>
|
<span class="identifier">v</span><span class="special">)</span> <span class="keyword">const</span><span class="special">&</span> <span class="special">;</span></code>
|
||||||
|
</p></blockquote></div>
|
||||||
|
<div class="blockquote"><blockquote class="blockquote"><p>
|
||||||
|
<code class="computeroutput"><span class="keyword">template</span><span class="special"><</span><span class="keyword">class</span> <span class="identifier">U</span><span class="special">></span> <span class="identifier">T</span> <span class="identifier">optional</span><span class="special"><</span><span class="identifier">T</span><span class="special">>::</span><span class="identifier">value_or</span><span class="special">(</span><span class="identifier">U</span> <span class="special">&&</span>
|
||||||
|
<span class="identifier">v</span><span class="special">)</span> <span class="special">&&</span> <span class="special">;</span></code>
|
||||||
</p></blockquote></div>
|
</p></blockquote></div>
|
||||||
<div class="itemizedlist"><ul class="itemizedlist" style="list-style-type: disc; ">
|
<div class="itemizedlist"><ul class="itemizedlist" style="list-style-type: disc; ">
|
||||||
<li class="listitem">
|
<li class="listitem">
|
||||||
@ -1284,17 +1404,22 @@
|
|||||||
is CopyConstructible.
|
is CopyConstructible.
|
||||||
</li>
|
</li>
|
||||||
<li class="listitem">
|
<li class="listitem">
|
||||||
<span class="bold"><strong>Returns:</strong></span> <code class="computeroutput"><span class="keyword">bool</span><span class="special">(*</span><span class="keyword">this</span><span class="special">)</span>
|
<span class="bold"><strong>Returns:</strong></span> First overload: <code class="computeroutput"><span class="keyword">bool</span><span class="special">(*</span><span class="keyword">this</span><span class="special">)</span> <span class="special">?</span> <span class="special">**</span><span class="keyword">this</span> <span class="special">:</span> <span class="keyword">static_cast</span><span class="special"><</span><span class="identifier">T</span><span class="special">>(</span><span class="identifier">forward</span><span class="special"><</span><span class="identifier">U</span><span class="special">>(</span><span class="identifier">v</span><span class="special">))</span></code>.
|
||||||
<span class="special">?</span> <span class="special">**</span><span class="keyword">this</span> <span class="special">:</span> <span class="keyword">static_cast</span><span class="special"><</span><span class="identifier">T</span><span class="special">>(</span><span class="identifier">forward</span><span class="special"><</span><span class="identifier">U</span><span class="special">>(</span><span class="identifier">v</span><span class="special">))</span></code>.
|
second overload: <code class="computeroutput"><span class="keyword">bool</span><span class="special">(*</span><span class="keyword">this</span><span class="special">)</span> <span class="special">?</span>
|
||||||
|
<span class="identifier">std</span><span class="special">::</span><span class="identifier">move</span><span class="special">(**</span><span class="keyword">this</span><span class="special">)</span> <span class="special">:</span>
|
||||||
|
<span class="keyword">static_cast</span><span class="special"><</span><span class="identifier">T</span><span class="special">>(</span><span class="identifier">forward</span><span class="special"><</span><span class="identifier">U</span><span class="special">>(</span><span class="identifier">v</span><span class="special">))</span></code>.
|
||||||
</li>
|
</li>
|
||||||
<li class="listitem">
|
<li class="listitem">
|
||||||
<span class="bold"><strong>Throws:</strong></span> Any exception thrown by the selected
|
<span class="bold"><strong>Throws:</strong></span> Any exception thrown by the selected
|
||||||
constructor of <code class="computeroutput"><span class="identifier">T</span></code>.
|
constructor of <code class="computeroutput"><span class="identifier">T</span></code>.
|
||||||
</li>
|
</li>
|
||||||
<li class="listitem">
|
<li class="listitem">
|
||||||
<span class="bold"><strong>Notes:</strong></span> On compilers without rvalue reference
|
<span class="bold"><strong>Notes:</strong></span> On compilers that do not support
|
||||||
support the type of <code class="computeroutput"><span class="identifier">v</span></code> becomes
|
ref-qualifiers on member functions these three overloads are replaced with
|
||||||
<code class="computeroutput"><span class="identifier">U</span> <span class="keyword">const</span><span class="special">&</span></code>.
|
the classical two: a <code class="computeroutput"><span class="keyword">const</span></code>
|
||||||
|
and non-<code class="computeroutput"><span class="keyword">const</span></code> member functions.
|
||||||
|
On compilers without rvalue reference support the type of <code class="computeroutput"><span class="identifier">v</span></code> becomes <code class="computeroutput"><span class="identifier">U</span>
|
||||||
|
<span class="keyword">const</span><span class="special">&</span></code>.
|
||||||
</li>
|
</li>
|
||||||
</ul></div>
|
</ul></div>
|
||||||
<p>
|
<p>
|
||||||
@ -1348,60 +1473,6 @@
|
|||||||
</pre>
|
</pre>
|
||||||
</li>
|
</li>
|
||||||
</ul></div>
|
</ul></div>
|
||||||
<p>
|
|
||||||
<span class="inlinemediaobject"><img src="../images/space.png" alt="space"></span>
|
|
||||||
</p>
|
|
||||||
<div class="blockquote"><blockquote class="blockquote"><p>
|
|
||||||
<code class="computeroutput"><span class="identifier">T</span> <span class="keyword">const</span><span class="special">&</span> <span class="identifier">optional</span><span class="special"><</span><span class="identifier">T</span><span class="special">&>::</span><span class="keyword">operator</span><span class="special">*()</span> <span class="keyword">const</span> <span class="special">;</span></code>
|
|
||||||
</p></blockquote></div>
|
|
||||||
<div class="blockquote"><blockquote class="blockquote"><p>
|
|
||||||
<code class="computeroutput"><span class="identifier">T</span> <span class="special">&</span>
|
|
||||||
<span class="identifier">optional</span><span class="special"><</span><span class="identifier">T</span><span class="special">&>::</span><span class="keyword">operator</span><span class="special">*();</span></code>
|
|
||||||
</p></blockquote></div>
|
|
||||||
<div class="blockquote"><blockquote class="blockquote"><p>
|
|
||||||
<code class="computeroutput"><span class="identifier">T</span> <span class="keyword">const</span><span class="special">&</span> <span class="identifier">optional</span><span class="special"><</span><span class="identifier">T</span><span class="special">&>::</span><span class="identifier">get</span><span class="special">()</span> <span class="keyword">const</span> <span class="special">;</span></code>
|
|
||||||
</p></blockquote></div>
|
|
||||||
<div class="blockquote"><blockquote class="blockquote"><p>
|
|
||||||
<code class="computeroutput"><span class="identifier">T</span><span class="special">&</span>
|
|
||||||
<span class="identifier">optional</span><span class="special"><</span><span class="identifier">T</span><span class="special">&>::</span><span class="identifier">get</span><span class="special">()</span> <span class="special">;</span></code>
|
|
||||||
</p></blockquote></div>
|
|
||||||
<div class="blockquote"><blockquote class="blockquote"><p>
|
|
||||||
<code class="computeroutput"><span class="keyword">inline</span> <span class="identifier">T</span>
|
|
||||||
<span class="keyword">const</span><span class="special">&</span>
|
|
||||||
<span class="identifier">get</span> <span class="special">(</span>
|
|
||||||
<span class="identifier">optional</span><span class="special"><</span><span class="identifier">T</span><span class="special">&></span> <span class="keyword">const</span><span class="special">&</span> <span class="special">)</span> <span class="special">;</span></code>
|
|
||||||
</p></blockquote></div>
|
|
||||||
<div class="blockquote"><blockquote class="blockquote"><p>
|
|
||||||
<code class="computeroutput"><span class="keyword">inline</span> <span class="identifier">T</span><span class="special">&</span> <span class="identifier">get</span> <span class="special">(</span> <span class="identifier">optional</span><span class="special"><</span><span class="identifier">T</span><span class="special">&></span>
|
|
||||||
<span class="special">&)</span> <span class="special">;</span></code>
|
|
||||||
</p></blockquote></div>
|
|
||||||
<div class="itemizedlist"><ul class="itemizedlist" style="list-style-type: disc; ">
|
|
||||||
<li class="listitem">
|
|
||||||
<span class="bold"><strong>Requires: </strong></span> <code class="computeroutput"><span class="special">*</span><span class="keyword">this</span></code> is initialized
|
|
||||||
</li>
|
|
||||||
<li class="listitem">
|
|
||||||
<span class="bold"><strong>Returns:</strong></span> <span class="underline">The</span>
|
|
||||||
reference contained.
|
|
||||||
</li>
|
|
||||||
<li class="listitem">
|
|
||||||
<span class="bold"><strong>Throws:</strong></span> Nothing.
|
|
||||||
</li>
|
|
||||||
<li class="listitem">
|
|
||||||
<span class="bold"><strong>Notes:</strong></span> The requirement is asserted via
|
|
||||||
<code class="computeroutput"><span class="identifier">BOOST_ASSERT</span><span class="special">()</span></code>.
|
|
||||||
</li>
|
|
||||||
<li class="listitem">
|
|
||||||
<span class="bold"><strong>Example:</strong></span>
|
|
||||||
<pre class="programlisting"><span class="identifier">T</span> <span class="identifier">v</span> <span class="special">;</span>
|
|
||||||
<span class="identifier">T</span><span class="special">&</span> <span class="identifier">vref</span> <span class="special">=</span> <span class="identifier">v</span> <span class="special">;</span>
|
|
||||||
<span class="identifier">optional</span><span class="special"><</span><span class="identifier">T</span><span class="special">&></span> <span class="identifier">opt</span> <span class="special">(</span> <span class="identifier">vref</span> <span class="special">);</span>
|
|
||||||
<span class="identifier">T</span> <span class="keyword">const</span><span class="special">&</span> <span class="identifier">vref2</span> <span class="special">=</span> <span class="special">*</span><span class="identifier">opt</span><span class="special">;</span>
|
|
||||||
<span class="identifier">assert</span> <span class="special">(</span> <span class="identifier">vref2</span> <span class="special">==</span> <span class="identifier">v</span> <span class="special">)</span> <span class="special">;</span>
|
|
||||||
<span class="special">++</span> <span class="identifier">v</span> <span class="special">;</span>
|
|
||||||
<span class="identifier">assert</span> <span class="special">(</span> <span class="special">*</span><span class="identifier">opt</span> <span class="special">==</span> <span class="identifier">v</span> <span class="special">)</span> <span class="special">;</span>
|
|
||||||
</pre>
|
|
||||||
</li>
|
|
||||||
</ul></div>
|
|
||||||
<p>
|
<p>
|
||||||
<span class="inlinemediaobject"><img src="../images/space.png" alt="space"></span>
|
<span class="inlinemediaobject"><img src="../images/space.png" alt="space"></span>
|
||||||
</p>
|
</p>
|
||||||
@ -1898,7 +1969,7 @@
|
|||||||
</tr></table>
|
</tr></table>
|
||||||
<hr>
|
<hr>
|
||||||
<div class="spirit-nav">
|
<div class="spirit-nav">
|
||||||
<a accesskey="p" href="synopsis.html"><img src="../../../../../doc/src/images/prev.png" alt="Prev"></a><a accesskey="u" href="../index.html"><img src="../../../../../doc/src/images/up.png" alt="Up"></a><a accesskey="h" href="../index.html"><img src="../../../../../doc/src/images/home.png" alt="Home"></a><a accesskey="n" href="examples.html"><img src="../../../../../doc/src/images/next.png" alt="Next"></a>
|
<a accesskey="p" href="synopsis.html"><img src="../../../../../doc/src/images/prev.png" alt="Prev"></a><a accesskey="u" href="../index.html"><img src="../../../../../doc/src/images/up.png" alt="Up"></a><a accesskey="h" href="../index.html"><img src="../../../../../doc/src/images/home.png" alt="Home"></a><a accesskey="n" href="dependencies_and_portability.html"><img src="../../../../../doc/src/images/next.png" alt="Next"></a>
|
||||||
</div>
|
</div>
|
||||||
</body>
|
</body>
|
||||||
</html>
|
</html>
|
||||||
|
@ -6,7 +6,7 @@
|
|||||||
<meta name="generator" content="DocBook XSL Stylesheets V1.78.1">
|
<meta name="generator" content="DocBook XSL Stylesheets V1.78.1">
|
||||||
<link rel="home" href="../index.html" title="Chapter 1. Boost.Optional">
|
<link rel="home" href="../index.html" title="Chapter 1. Boost.Optional">
|
||||||
<link rel="up" href="../index.html" title="Chapter 1. Boost.Optional">
|
<link rel="up" href="../index.html" title="Chapter 1. Boost.Optional">
|
||||||
<link rel="prev" href="discussion.html" title="Discussion">
|
<link rel="prev" href="tutorial.html" title="Tutorial">
|
||||||
<link rel="next" href="synopsis.html" title="Synopsis">
|
<link rel="next" href="synopsis.html" title="Synopsis">
|
||||||
</head>
|
</head>
|
||||||
<body bgcolor="white" text="black" link="#0000FF" vlink="#840084" alink="#0000FF">
|
<body bgcolor="white" text="black" link="#0000FF" vlink="#840084" alink="#0000FF">
|
||||||
@ -20,7 +20,7 @@
|
|||||||
</tr></table>
|
</tr></table>
|
||||||
<hr>
|
<hr>
|
||||||
<div class="spirit-nav">
|
<div class="spirit-nav">
|
||||||
<a accesskey="p" href="discussion.html"><img src="../../../../../doc/src/images/prev.png" alt="Prev"></a><a accesskey="u" href="../index.html"><img src="../../../../../doc/src/images/up.png" alt="Up"></a><a accesskey="h" href="../index.html"><img src="../../../../../doc/src/images/home.png" alt="Home"></a><a accesskey="n" href="synopsis.html"><img src="../../../../../doc/src/images/next.png" alt="Next"></a>
|
<a accesskey="p" href="tutorial.html"><img src="../../../../../doc/src/images/prev.png" alt="Prev"></a><a accesskey="u" href="../index.html"><img src="../../../../../doc/src/images/up.png" alt="Up"></a><a accesskey="h" href="../index.html"><img src="../../../../../doc/src/images/home.png" alt="Home"></a><a accesskey="n" href="synopsis.html"><img src="../../../../../doc/src/images/next.png" alt="Next"></a>
|
||||||
</div>
|
</div>
|
||||||
<div class="section">
|
<div class="section">
|
||||||
<div class="titlepage"><div><div><h2 class="title" style="clear: both">
|
<div class="titlepage"><div><div><h2 class="title" style="clear: both">
|
||||||
@ -406,7 +406,7 @@
|
|||||||
</tr></table>
|
</tr></table>
|
||||||
<hr>
|
<hr>
|
||||||
<div class="spirit-nav">
|
<div class="spirit-nav">
|
||||||
<a accesskey="p" href="discussion.html"><img src="../../../../../doc/src/images/prev.png" alt="Prev"></a><a accesskey="u" href="../index.html"><img src="../../../../../doc/src/images/up.png" alt="Up"></a><a accesskey="h" href="../index.html"><img src="../../../../../doc/src/images/home.png" alt="Home"></a><a accesskey="n" href="synopsis.html"><img src="../../../../../doc/src/images/next.png" alt="Next"></a>
|
<a accesskey="p" href="tutorial.html"><img src="../../../../../doc/src/images/prev.png" alt="Prev"></a><a accesskey="u" href="../index.html"><img src="../../../../../doc/src/images/up.png" alt="Up"></a><a accesskey="h" href="../index.html"><img src="../../../../../doc/src/images/home.png" alt="Home"></a><a accesskey="n" href="synopsis.html"><img src="../../../../../doc/src/images/next.png" alt="Next"></a>
|
||||||
</div>
|
</div>
|
||||||
</body>
|
</body>
|
||||||
</html>
|
</html>
|
||||||
|
@ -6,7 +6,7 @@
|
|||||||
<meta name="generator" content="DocBook XSL Stylesheets V1.78.1">
|
<meta name="generator" content="DocBook XSL Stylesheets V1.78.1">
|
||||||
<link rel="home" href="../index.html" title="Chapter 1. Boost.Optional">
|
<link rel="home" href="../index.html" title="Chapter 1. Boost.Optional">
|
||||||
<link rel="up" href="../index.html" title="Chapter 1. Boost.Optional">
|
<link rel="up" href="../index.html" title="Chapter 1. Boost.Optional">
|
||||||
<link rel="prev" href="tutorial.html" title="Tutorial">
|
<link rel="prev" href="quick_start.html" title="Quick Start">
|
||||||
<link rel="next" href="development.html" title="Development">
|
<link rel="next" href="development.html" title="Development">
|
||||||
</head>
|
</head>
|
||||||
<body bgcolor="white" text="black" link="#0000FF" vlink="#840084" alink="#0000FF">
|
<body bgcolor="white" text="black" link="#0000FF" vlink="#840084" alink="#0000FF">
|
||||||
@ -20,7 +20,7 @@
|
|||||||
</tr></table>
|
</tr></table>
|
||||||
<hr>
|
<hr>
|
||||||
<div class="spirit-nav">
|
<div class="spirit-nav">
|
||||||
<a accesskey="p" href="tutorial.html"><img src="../../../../../doc/src/images/prev.png" alt="Prev"></a><a accesskey="u" href="../index.html"><img src="../../../../../doc/src/images/up.png" alt="Up"></a><a accesskey="h" href="../index.html"><img src="../../../../../doc/src/images/home.png" alt="Home"></a><a accesskey="n" href="development.html"><img src="../../../../../doc/src/images/next.png" alt="Next"></a>
|
<a accesskey="p" href="quick_start.html"><img src="../../../../../doc/src/images/prev.png" alt="Prev"></a><a accesskey="u" href="../index.html"><img src="../../../../../doc/src/images/up.png" alt="Up"></a><a accesskey="h" href="../index.html"><img src="../../../../../doc/src/images/home.png" alt="Home"></a><a accesskey="n" href="development.html"><img src="../../../../../doc/src/images/next.png" alt="Next"></a>
|
||||||
</div>
|
</div>
|
||||||
<div class="section">
|
<div class="section">
|
||||||
<div class="titlepage"><div><div><h2 class="title" style="clear: both">
|
<div class="titlepage"><div><div><h2 class="title" style="clear: both">
|
||||||
@ -122,7 +122,7 @@
|
|||||||
</tr></table>
|
</tr></table>
|
||||||
<hr>
|
<hr>
|
||||||
<div class="spirit-nav">
|
<div class="spirit-nav">
|
||||||
<a accesskey="p" href="tutorial.html"><img src="../../../../../doc/src/images/prev.png" alt="Prev"></a><a accesskey="u" href="../index.html"><img src="../../../../../doc/src/images/up.png" alt="Up"></a><a accesskey="h" href="../index.html"><img src="../../../../../doc/src/images/home.png" alt="Home"></a><a accesskey="n" href="development.html"><img src="../../../../../doc/src/images/next.png" alt="Next"></a>
|
<a accesskey="p" href="quick_start.html"><img src="../../../../../doc/src/images/prev.png" alt="Prev"></a><a accesskey="u" href="../index.html"><img src="../../../../../doc/src/images/up.png" alt="Up"></a><a accesskey="h" href="../index.html"><img src="../../../../../doc/src/images/home.png" alt="Home"></a><a accesskey="n" href="development.html"><img src="../../../../../doc/src/images/next.png" alt="Next"></a>
|
||||||
</div>
|
</div>
|
||||||
</body>
|
</body>
|
||||||
</html>
|
</html>
|
||||||
|
@ -6,7 +6,7 @@
|
|||||||
<meta name="generator" content="DocBook XSL Stylesheets V1.78.1">
|
<meta name="generator" content="DocBook XSL Stylesheets V1.78.1">
|
||||||
<link rel="home" href="../index.html" title="Chapter 1. Boost.Optional">
|
<link rel="home" href="../index.html" title="Chapter 1. Boost.Optional">
|
||||||
<link rel="up" href="../index.html" title="Chapter 1. Boost.Optional">
|
<link rel="up" href="../index.html" title="Chapter 1. Boost.Optional">
|
||||||
<link rel="prev" href="rebinding_semantics_for_assignment_of_optional_references.html" title="Rebinding semantics for assignment of optional references">
|
<link rel="prev" href="detailed_semantics.html" title="Detailed Semantics">
|
||||||
<link rel="next" href="a_note_about_optional_bool_.html" title="A note about optional<bool>">
|
<link rel="next" href="a_note_about_optional_bool_.html" title="A note about optional<bool>">
|
||||||
</head>
|
</head>
|
||||||
<body bgcolor="white" text="black" link="#0000FF" vlink="#840084" alink="#0000FF">
|
<body bgcolor="white" text="black" link="#0000FF" vlink="#840084" alink="#0000FF">
|
||||||
@ -20,7 +20,7 @@
|
|||||||
</tr></table>
|
</tr></table>
|
||||||
<hr>
|
<hr>
|
||||||
<div class="spirit-nav">
|
<div class="spirit-nav">
|
||||||
<a accesskey="p" href="rebinding_semantics_for_assignment_of_optional_references.html"><img src="../../../../../doc/src/images/prev.png" alt="Prev"></a><a accesskey="u" href="../index.html"><img src="../../../../../doc/src/images/up.png" alt="Up"></a><a accesskey="h" href="../index.html"><img src="../../../../../doc/src/images/home.png" alt="Home"></a><a accesskey="n" href="a_note_about_optional_bool_.html"><img src="../../../../../doc/src/images/next.png" alt="Next"></a>
|
<a accesskey="p" href="detailed_semantics.html"><img src="../../../../../doc/src/images/prev.png" alt="Prev"></a><a accesskey="u" href="../index.html"><img src="../../../../../doc/src/images/up.png" alt="Up"></a><a accesskey="h" href="../index.html"><img src="../../../../../doc/src/images/home.png" alt="Home"></a><a accesskey="n" href="a_note_about_optional_bool_.html"><img src="../../../../../doc/src/images/next.png" alt="Next"></a>
|
||||||
</div>
|
</div>
|
||||||
<div class="section">
|
<div class="section">
|
||||||
<div class="titlepage"><div><div><h2 class="title" style="clear: both">
|
<div class="titlepage"><div><div><h2 class="title" style="clear: both">
|
||||||
@ -190,7 +190,7 @@
|
|||||||
</tr></table>
|
</tr></table>
|
||||||
<hr>
|
<hr>
|
||||||
<div class="spirit-nav">
|
<div class="spirit-nav">
|
||||||
<a accesskey="p" href="rebinding_semantics_for_assignment_of_optional_references.html"><img src="../../../../../doc/src/images/prev.png" alt="Prev"></a><a accesskey="u" href="../index.html"><img src="../../../../../doc/src/images/up.png" alt="Up"></a><a accesskey="h" href="../index.html"><img src="../../../../../doc/src/images/home.png" alt="Home"></a><a accesskey="n" href="a_note_about_optional_bool_.html"><img src="../../../../../doc/src/images/next.png" alt="Next"></a>
|
<a accesskey="p" href="detailed_semantics.html"><img src="../../../../../doc/src/images/prev.png" alt="Prev"></a><a accesskey="u" href="../index.html"><img src="../../../../../doc/src/images/up.png" alt="Up"></a><a accesskey="h" href="../index.html"><img src="../../../../../doc/src/images/home.png" alt="Home"></a><a accesskey="n" href="a_note_about_optional_bool_.html"><img src="../../../../../doc/src/images/next.png" alt="Next"></a>
|
||||||
</div>
|
</div>
|
||||||
</body>
|
</body>
|
||||||
</html>
|
</html>
|
||||||
|
@ -6,7 +6,7 @@
|
|||||||
<meta name="generator" content="DocBook XSL Stylesheets V1.78.1">
|
<meta name="generator" content="DocBook XSL Stylesheets V1.78.1">
|
||||||
<link rel="home" href="../index.html" title="Chapter 1. Boost.Optional">
|
<link rel="home" href="../index.html" title="Chapter 1. Boost.Optional">
|
||||||
<link rel="up" href="../index.html" title="Chapter 1. Boost.Optional">
|
<link rel="up" href="../index.html" title="Chapter 1. Boost.Optional">
|
||||||
<link rel="prev" href="examples.html" title="Examples">
|
<link rel="prev" href="detailed_semantics.html" title="Detailed Semantics">
|
||||||
<link rel="next" href="rebinding_semantics_for_assignment_of_optional_references.html" title="Rebinding semantics for assignment of optional references">
|
<link rel="next" href="rebinding_semantics_for_assignment_of_optional_references.html" title="Rebinding semantics for assignment of optional references">
|
||||||
</head>
|
</head>
|
||||||
<body bgcolor="white" text="black" link="#0000FF" vlink="#840084" alink="#0000FF">
|
<body bgcolor="white" text="black" link="#0000FF" vlink="#840084" alink="#0000FF">
|
||||||
@ -20,7 +20,7 @@
|
|||||||
</tr></table>
|
</tr></table>
|
||||||
<hr>
|
<hr>
|
||||||
<div class="spirit-nav">
|
<div class="spirit-nav">
|
||||||
<a accesskey="p" href="examples.html"><img src="../../../../../doc/src/images/prev.png" alt="Prev"></a><a accesskey="u" href="../index.html"><img src="../../../../../doc/src/images/up.png" alt="Up"></a><a accesskey="h" href="../index.html"><img src="../../../../../doc/src/images/home.png" alt="Home"></a><a accesskey="n" href="rebinding_semantics_for_assignment_of_optional_references.html"><img src="../../../../../doc/src/images/next.png" alt="Next"></a>
|
<a accesskey="p" href="detailed_semantics.html"><img src="../../../../../doc/src/images/prev.png" alt="Prev"></a><a accesskey="u" href="../index.html"><img src="../../../../../doc/src/images/up.png" alt="Up"></a><a accesskey="h" href="../index.html"><img src="../../../../../doc/src/images/home.png" alt="Home"></a><a accesskey="n" href="rebinding_semantics_for_assignment_of_optional_references.html"><img src="../../../../../doc/src/images/next.png" alt="Next"></a>
|
||||||
</div>
|
</div>
|
||||||
<div class="section">
|
<div class="section">
|
||||||
<div class="titlepage"><div><div><h2 class="title" style="clear: both">
|
<div class="titlepage"><div><div><h2 class="title" style="clear: both">
|
||||||
@ -77,7 +77,7 @@
|
|||||||
On compilers that do not conform to Standard C++ rules of reference binding,
|
On compilers that do not conform to Standard C++ rules of reference binding,
|
||||||
operations on optional references might give adverse results: rather than
|
operations on optional references might give adverse results: rather than
|
||||||
binding a reference to a designated object they may create an unexpected
|
binding a reference to a designated object they may create an unexpected
|
||||||
temporary and bind to it. For more details see <a class="link" href="dependencies_and_portability.html#boost_optional.dependencies_and_portability.optional_reference_binding" title="Optional Reference Binding">Dependencies
|
temporary and bind to it. For more details see <a class="link" href="dependencies_and_portability/optional_reference_binding.html" title="Optional Reference Binding">Dependencies
|
||||||
and Portability section</a>.
|
and Portability section</a>.
|
||||||
</p></td></tr>
|
</p></td></tr>
|
||||||
</table></div>
|
</table></div>
|
||||||
@ -108,7 +108,7 @@
|
|||||||
</tr></table>
|
</tr></table>
|
||||||
<hr>
|
<hr>
|
||||||
<div class="spirit-nav">
|
<div class="spirit-nav">
|
||||||
<a accesskey="p" href="examples.html"><img src="../../../../../doc/src/images/prev.png" alt="Prev"></a><a accesskey="u" href="../index.html"><img src="../../../../../doc/src/images/up.png" alt="Up"></a><a accesskey="h" href="../index.html"><img src="../../../../../doc/src/images/home.png" alt="Home"></a><a accesskey="n" href="rebinding_semantics_for_assignment_of_optional_references.html"><img src="../../../../../doc/src/images/next.png" alt="Next"></a>
|
<a accesskey="p" href="detailed_semantics.html"><img src="../../../../../doc/src/images/prev.png" alt="Prev"></a><a accesskey="u" href="../index.html"><img src="../../../../../doc/src/images/up.png" alt="Up"></a><a accesskey="h" href="../index.html"><img src="../../../../../doc/src/images/home.png" alt="Home"></a><a accesskey="n" href="rebinding_semantics_for_assignment_of_optional_references.html"><img src="../../../../../doc/src/images/next.png" alt="Next"></a>
|
||||||
</div>
|
</div>
|
||||||
</body>
|
</body>
|
||||||
</html>
|
</html>
|
||||||
|
261
doc/html/boost_optional/quick_start.html
Normal file
261
doc/html/boost_optional/quick_start.html
Normal file
@ -0,0 +1,261 @@
|
|||||||
|
<html>
|
||||||
|
<head>
|
||||||
|
<meta http-equiv="Content-Type" content="text/html; charset=US-ASCII">
|
||||||
|
<title>Quick Start</title>
|
||||||
|
<link rel="stylesheet" href="../../../../../doc/src/boostbook.css" type="text/css">
|
||||||
|
<meta name="generator" content="DocBook XSL Stylesheets V1.78.1">
|
||||||
|
<link rel="home" href="../index.html" title="Chapter 1. Boost.Optional">
|
||||||
|
<link rel="up" href="../index.html" title="Chapter 1. Boost.Optional">
|
||||||
|
<link rel="prev" href="../index.html" title="Chapter 1. Boost.Optional">
|
||||||
|
<link rel="next" href="../optional/tutorial.html" title="Tutorial">
|
||||||
|
</head>
|
||||||
|
<body bgcolor="white" text="black" link="#0000FF" vlink="#840084" alink="#0000FF">
|
||||||
|
<table cellpadding="2" width="100%"><tr>
|
||||||
|
<td valign="top"><img alt="Boost C++ Libraries" width="277" height="86" src="../../../../../boost.png"></td>
|
||||||
|
<td align="center"><a href="../../../../../index.html">Home</a></td>
|
||||||
|
<td align="center"><a href="../../../../../libs/libraries.htm">Libraries</a></td>
|
||||||
|
<td align="center"><a href="http://www.boost.org/users/people.html">People</a></td>
|
||||||
|
<td align="center"><a href="http://www.boost.org/users/faq.html">FAQ</a></td>
|
||||||
|
<td align="center"><a href="../../../../../more/index.htm">More</a></td>
|
||||||
|
</tr></table>
|
||||||
|
<hr>
|
||||||
|
<div class="spirit-nav">
|
||||||
|
<a accesskey="p" href="../index.html"><img src="../../../../../doc/src/images/prev.png" alt="Prev"></a><a accesskey="u" href="../index.html"><img src="../../../../../doc/src/images/up.png" alt="Up"></a><a accesskey="h" href="../index.html"><img src="../../../../../doc/src/images/home.png" alt="Home"></a><a accesskey="n" href="../optional/tutorial.html"><img src="../../../../../doc/src/images/next.png" alt="Next"></a>
|
||||||
|
</div>
|
||||||
|
<div class="section">
|
||||||
|
<div class="titlepage"><div><div><h2 class="title" style="clear: both">
|
||||||
|
<a name="boost_optional.quick_start"></a><a class="link" href="quick_start.html" title="Quick Start">Quick Start</a>
|
||||||
|
</h2></div></div></div>
|
||||||
|
<h4>
|
||||||
|
<a name="boost_optional.quick_start.h0"></a>
|
||||||
|
<span class="phrase"><a name="boost_optional.quick_start.optional_return_values"></a></span><a class="link" href="quick_start.html#boost_optional.quick_start.optional_return_values">Optional
|
||||||
|
return values</a>
|
||||||
|
</h4>
|
||||||
|
<p>
|
||||||
|
Let's write and use a converter function that converts an a <code class="computeroutput"><span class="identifier">std</span><span class="special">::</span><span class="identifier">string</span></code>
|
||||||
|
to an <code class="computeroutput"><span class="keyword">int</span></code>. It is possible that
|
||||||
|
for a given string (e.g. <code class="computeroutput"><span class="string">"cat"</span></code>)
|
||||||
|
there exist no value of type <code class="computeroutput"><span class="keyword">int</span></code>
|
||||||
|
capable of representing the conversion result. We do not consider such situation
|
||||||
|
an error. We expect that the converter can be used only to check if the conversion
|
||||||
|
is possible. A natural signature for this function can be:
|
||||||
|
</p>
|
||||||
|
<pre class="programlisting"><span class="preprocessor">#include</span> <span class="special"><</span><span class="identifier">boost</span><span class="special">/</span><span class="identifier">optional</span><span class="special">.</span><span class="identifier">hpp</span><span class="special">></span>
|
||||||
|
<span class="identifier">boost</span><span class="special">::</span><span class="identifier">optionl</span><span class="special"><</span><span class="keyword">int</span><span class="special">></span> <span class="identifier">convert</span><span class="special">(</span><span class="keyword">const</span> <span class="identifier">std</span><span class="special">::</span><span class="identifier">string</span><span class="special">&</span> <span class="identifier">text</span><span class="special">);</span>
|
||||||
|
</pre>
|
||||||
|
<p>
|
||||||
|
All necessary functionality can be included with one header <code class="computeroutput"><span class="special"><</span><span class="identifier">boost</span><span class="special">/</span><span class="identifier">optional</span><span class="special">.</span><span class="identifier">hpp</span><span class="special">></span></code>.
|
||||||
|
The above function signature means that the function can either return a value
|
||||||
|
of type <code class="computeroutput"><span class="keyword">int</span></code> or a flag indicating
|
||||||
|
that no value of <code class="computeroutput"><span class="keyword">int</span></code> is available.
|
||||||
|
This does not indicate an error. It is like one additional value of <code class="computeroutput"><span class="keyword">int</span></code>. This is how we can use our function:
|
||||||
|
</p>
|
||||||
|
<pre class="programlisting"><span class="keyword">const</span> <span class="identifier">std</span><span class="special">::</span><span class="identifier">string</span><span class="special">&</span> <span class="identifier">text</span> <span class="special">=</span> <span class="comment">/*... */</span><span class="special">;</span>
|
||||||
|
<span class="identifier">boost</span><span class="special">::</span><span class="identifier">optionl</span><span class="special"><</span><span class="keyword">int</span><span class="special">></span> <span class="identifier">oi</span> <span class="special">=</span> <span class="identifier">convert</span><span class="special">(</span><span class="identifier">text</span><span class="special">);</span> <span class="comment">// move-construct</span>
|
||||||
|
<span class="keyword">if</span> <span class="special">(</span><span class="identifier">oi</span><span class="special">)</span> <span class="comment">// contextual conversion to bool</span>
|
||||||
|
<span class="keyword">int</span> <span class="identifier">i</span> <span class="special">=</span> <span class="special">*</span><span class="identifier">oi</span><span class="special">;</span> <span class="comment">// operator*</span>
|
||||||
|
</pre>
|
||||||
|
<p>
|
||||||
|
In order to test if <code class="computeroutput"><span class="identifier">optional</span></code>
|
||||||
|
contains a value, we use the contextual conversion to type <code class="computeroutput"><span class="keyword">bool</span></code>.
|
||||||
|
Because of this we can combine the initialization of the optional object and
|
||||||
|
the test into one instruction:
|
||||||
|
</p>
|
||||||
|
<pre class="programlisting"><span class="keyword">if</span> <span class="special">(</span><span class="identifier">boost</span><span class="special">::</span><span class="identifier">optionl</span><span class="special"><</span><span class="keyword">int</span><span class="special">></span> <span class="identifier">oi</span> <span class="special">=</span> <span class="identifier">convert</span><span class="special">(</span><span class="identifier">text</span><span class="special">))</span>
|
||||||
|
<span class="keyword">int</span> <span class="identifier">i</span> <span class="special">=</span> <span class="special">*</span><span class="identifier">oi</span><span class="special">;</span>
|
||||||
|
</pre>
|
||||||
|
<p>
|
||||||
|
We extract the contained value with <code class="computeroutput"><span class="keyword">operator</span><span class="special">*</span></code> (and with <code class="computeroutput"><span class="keyword">operator</span><span class="special">-></span></code> where it makes sense). An attempt to extract
|
||||||
|
the contained value of an uninitialized optional object is an <span class="emphasis"><em>undefined
|
||||||
|
behaviour</em></span> (UB). This implementation guards the call with <code class="computeroutput"><span class="identifier">BOOST_ASSERT</span></code>. Therefore you should be sure
|
||||||
|
that the contained value is there before extracting. For instance, the following
|
||||||
|
code is reasonably UB-safe:
|
||||||
|
</p>
|
||||||
|
<pre class="programlisting"><span class="keyword">int</span> <span class="identifier">i</span> <span class="special">=</span> <span class="special">*</span><span class="identifier">convert</span><span class="special">(</span><span class="string">"100"</span><span class="special">);</span>
|
||||||
|
</pre>
|
||||||
|
<p>
|
||||||
|
This is because we know that string value <code class="computeroutput"><span class="string">"100"</span></code>
|
||||||
|
converts to a valid value of <code class="computeroutput"><span class="keyword">int</span></code>.
|
||||||
|
If you do not like this potential UB, you can use an alternative way of extracting
|
||||||
|
the contained value:
|
||||||
|
</p>
|
||||||
|
<pre class="programlisting"><span class="keyword">try</span> <span class="special">{</span>
|
||||||
|
<span class="keyword">int</span> <span class="identifier">j</span> <span class="special">=</span> <span class="identifier">convert</span><span class="special">(</span><span class="identifier">text</span><span class="special">).</span><span class="identifier">value</span><span class="special">();</span>
|
||||||
|
<span class="special">}</span>
|
||||||
|
<span class="keyword">catch</span> <span class="special">(</span><span class="keyword">const</span> <span class="identifier">boost</span><span class="special">::</span><span class="identifier">bad_optional_access</span><span class="special">&)</span> <span class="special">{</span>
|
||||||
|
<span class="comment">// deal with it</span>
|
||||||
|
<span class="special">}</span>
|
||||||
|
</pre>
|
||||||
|
<p>
|
||||||
|
This version throws an exception upon an attempt to access a non-existent contained
|
||||||
|
value. If your way of dealing with the missing value is to use some default,
|
||||||
|
like <code class="computeroutput"><span class="number">0</span></code>, there exists a yet another
|
||||||
|
alternative:
|
||||||
|
</p>
|
||||||
|
<pre class="programlisting"><span class="keyword">int</span> <span class="identifier">k</span> <span class="special">=</span> <span class="identifier">convert</span><span class="special">(</span><span class="identifier">text</span><span class="special">).</span><span class="identifier">value_or</span><span class="special">(</span><span class="number">0</span><span class="special">);</span>
|
||||||
|
</pre>
|
||||||
|
<p>
|
||||||
|
This uses the <code class="computeroutput"><span class="identifier">atoi</span></code>-like approach
|
||||||
|
to conversions: if <code class="computeroutput"><span class="identifier">text</span></code> does
|
||||||
|
not represent an integral number just return <code class="computeroutput"><span class="number">0</span></code>.
|
||||||
|
Now, let's consider how function <code class="computeroutput"><span class="identifier">convert</span></code>
|
||||||
|
can be implemented.
|
||||||
|
</p>
|
||||||
|
<pre class="programlisting"><span class="identifier">boost</span><span class="special">::</span><span class="identifier">optionl</span><span class="special"><</span><span class="keyword">int</span><span class="special">></span> <span class="identifier">convert</span><span class="special">(</span><span class="keyword">const</span> <span class="identifier">std</span><span class="special">::</span><span class="identifier">string</span><span class="special">&</span> <span class="identifier">text</span><span class="special">)</span>
|
||||||
|
<span class="special">{</span>
|
||||||
|
<span class="identifier">std</span><span class="special">::</span><span class="identifier">stringstream</span> <span class="identifier">s</span><span class="special">(</span><span class="identifier">text</span><span class="special">);</span>
|
||||||
|
<span class="keyword">int</span> <span class="identifier">i</span><span class="special">;</span>
|
||||||
|
<span class="keyword">if</span> <span class="special">((</span><span class="identifier">s</span> <span class="special">>></span> <span class="identifier">i</span><span class="special">)</span> <span class="special">&&</span> <span class="identifier">s</span><span class="special">.</span><span class="identifier">get</span><span class="special">()</span> <span class="special">==</span> <span class="identifier">std</span><span class="special">::</span><span class="identifier">char_traits</span><span class="special"><</span><span class="keyword">char</span><span class="special">>::</span><span class="identifier">eof</span><span class="special">())</span>
|
||||||
|
<span class="keyword">return</span> <span class="identifier">i</span><span class="special">;</span>
|
||||||
|
<span class="keyword">else</span>
|
||||||
|
<span class="keyword">return</span> <span class="identifier">boost</span><span class="special">::</span><span class="identifier">none</span><span class="special">;</span>
|
||||||
|
<span class="special">}</span>
|
||||||
|
</pre>
|
||||||
|
<p>
|
||||||
|
Observe the two return statements. <code class="computeroutput"><span class="keyword">return</span>
|
||||||
|
<span class="identifier">i</span></code> uses the converting constructor
|
||||||
|
that can create <code class="computeroutput"><span class="identifier">optional</span><span class="special"><</span><span class="identifier">T</span><span class="special">></span></code> from
|
||||||
|
<code class="computeroutput"><span class="identifier">T</span></code>. Thus constructed optional
|
||||||
|
object is initialized and its value is a copy of <code class="computeroutput"><span class="identifier">i</span></code>.
|
||||||
|
The other return statement uses another converting constructor from a special
|
||||||
|
tag <code class="computeroutput"><span class="identifier">boost</span><span class="special">::</span><span class="identifier">none</span></code>. It is used to indicate that we want
|
||||||
|
to create an uninitialized optional object.
|
||||||
|
</p>
|
||||||
|
<h4>
|
||||||
|
<a name="boost_optional.quick_start.h1"></a>
|
||||||
|
<span class="phrase"><a name="boost_optional.quick_start.optional_automatic_variables"></a></span><a class="link" href="quick_start.html#boost_optional.quick_start.optional_automatic_variables">Optional
|
||||||
|
automatic variables</a>
|
||||||
|
</h4>
|
||||||
|
<p>
|
||||||
|
We could write function <code class="computeroutput"><span class="identifier">convert</span></code>
|
||||||
|
in a slightly different manner, so that it has a single <code class="computeroutput"><span class="keyword">return</span></code>-statement:
|
||||||
|
</p>
|
||||||
|
<pre class="programlisting"><span class="identifier">boost</span><span class="special">::</span><span class="identifier">optionl</span><span class="special"><</span><span class="keyword">int</span><span class="special">></span> <span class="identifier">convert</span><span class="special">(</span><span class="keyword">const</span> <span class="identifier">std</span><span class="special">::</span><span class="identifier">string</span><span class="special">&</span> <span class="identifier">text</span><span class="special">)</span>
|
||||||
|
<span class="special">{</span>
|
||||||
|
<span class="identifier">boost</span><span class="special">::</span><span class="identifier">optionl</span><span class="special"><</span><span class="keyword">int</span><span class="special">></span> <span class="identifier">ans</span><span class="special">;</span>
|
||||||
|
<span class="identifier">std</span><span class="special">::</span><span class="identifier">stringstream</span> <span class="identifier">s</span><span class="special">(</span><span class="identifier">text</span><span class="special">);</span>
|
||||||
|
<span class="keyword">int</span> <span class="identifier">i</span><span class="special">;</span>
|
||||||
|
<span class="keyword">if</span> <span class="special">((</span><span class="identifier">s</span> <span class="special">>></span> <span class="identifier">i</span><span class="special">)</span> <span class="special">&&</span> <span class="identifier">s</span><span class="special">.</span><span class="identifier">get</span><span class="special">()</span> <span class="special">==</span> <span class="identifier">std</span><span class="special">::</span><span class="identifier">char_traits</span><span class="special"><</span><span class="keyword">char</span><span class="special">>::</span><span class="identifier">eof</span><span class="special">())</span>
|
||||||
|
<span class="identifier">ans</span> <span class="special">=</span> <span class="identifier">i</span><span class="special">;</span>
|
||||||
|
|
||||||
|
<span class="keyword">return</span> <span class="identifier">ans</span><span class="special">;</span>
|
||||||
|
<span class="special">}</span>
|
||||||
|
</pre>
|
||||||
|
<p>
|
||||||
|
The default constructor of <code class="computeroutput"><span class="identifier">optional</span></code>
|
||||||
|
creates an unitialized optional object. Unlike with <code class="computeroutput"><span class="keyword">int</span></code>s
|
||||||
|
you cannot have an <code class="computeroutput"><span class="identifier">optional</span><span class="special"><</span><span class="keyword">int</span><span class="special">></span></code>
|
||||||
|
in an indeterminate state. Its state is always well defined. Instruction <code class="computeroutput"><span class="identifier">ans</span> <span class="special">=</span> <span class="identifier">i</span></code>
|
||||||
|
initializes the optional object. It uses the assignment from <code class="computeroutput"><span class="keyword">int</span></code>. In general, for <code class="computeroutput"><span class="identifier">optional</span><span class="special"><</span><span class="identifier">T</span><span class="special">></span></code>,
|
||||||
|
when an assignment from <code class="computeroutput"><span class="identifier">T</span></code> is
|
||||||
|
invoked, it can do two things. If the optional object is not initialized our
|
||||||
|
case here), it initializes it with <code class="computeroutput"><span class="identifier">T</span></code>'s
|
||||||
|
copy constructor. If the optional object is already initialized, it assigns
|
||||||
|
the new value to it using <code class="computeroutput"><span class="identifier">T</span></code>'s
|
||||||
|
copy assignment.
|
||||||
|
</p>
|
||||||
|
<h4>
|
||||||
|
<a name="boost_optional.quick_start.h2"></a>
|
||||||
|
<span class="phrase"><a name="boost_optional.quick_start.optional_data_members"></a></span><a class="link" href="quick_start.html#boost_optional.quick_start.optional_data_members">Optional
|
||||||
|
data members</a>
|
||||||
|
</h4>
|
||||||
|
<p>
|
||||||
|
Suppose we want to implement a <span class="emphasis"><em>lazy load</em></span> optimization.
|
||||||
|
This is because we do not want to perform an expensive initialization of our
|
||||||
|
<code class="computeroutput"><span class="identifier">Resource</span></code> until (if at all)
|
||||||
|
it is really used. We can do it this way:
|
||||||
|
</p>
|
||||||
|
<pre class="programlisting"><span class="keyword">class</span> <span class="identifier">Widget</span>
|
||||||
|
<span class="special">{</span>
|
||||||
|
<span class="identifier">boost</span><span class="special">::</span><span class="identifier">optional</span><span class="special"><</span><span class="identifier">Resource</span><span class="special">></span> <span class="identifier">resource_</span><span class="special">;</span>
|
||||||
|
|
||||||
|
<span class="keyword">public</span><span class="special">:</span>
|
||||||
|
<span class="identifier">Widget</span><span class="special">()</span> <span class="special">{}</span>
|
||||||
|
|
||||||
|
<span class="identifier">Resource</span><span class="special">&</span> <span class="identifier">getResource</span><span class="special">()</span> <span class="comment">// not thread-safe</span>
|
||||||
|
<span class="special">{</span>
|
||||||
|
<span class="keyword">if</span> <span class="special">(</span><span class="identifier">resource_</span> <span class="special">==</span> <span class="identifier">boost</span><span class="special">::</span><span class="identifier">none</span><span class="special">)</span>
|
||||||
|
<span class="identifier">resource_</span><span class="special">.</span><span class="identifier">emplace</span><span class="special">(</span><span class="string">"resource"</span><span class="special">,</span> <span class="string">"arguments"</span><span class="special">);</span>
|
||||||
|
|
||||||
|
<span class="keyword">return</span> <span class="special">*</span><span class="identifier">resource_</span><span class="special">;</span>
|
||||||
|
<span class="special">}</span>
|
||||||
|
<span class="special">};</span>
|
||||||
|
</pre>
|
||||||
|
<p>
|
||||||
|
<code class="computeroutput"><span class="identifier">optional</span></code>'s default constructor
|
||||||
|
creates an uninitialized optional. No call to <code class="computeroutput"><span class="identifier">Resource</span></code>'s
|
||||||
|
default constructor is attempted. <code class="computeroutput"><span class="identifier">Resource</span></code>
|
||||||
|
doesn't have to be <a href="http://www.sgi.com/tech/stl/DefaultConstructible.html" target="_top">Default
|
||||||
|
Constructible</a>. In function <code class="computeroutput"><span class="identifier">getResource</span></code>
|
||||||
|
we first check if <code class="computeroutput"><span class="identifier">resource_</span></code>
|
||||||
|
is initialized. This time we do not use the contextual conversion to <code class="computeroutput"><span class="keyword">bool</span></code>, but a comparison with <code class="computeroutput"><span class="identifier">boost</span><span class="special">::</span><span class="identifier">none</span></code>. These
|
||||||
|
two ways are equivalent. Function <code class="computeroutput"><span class="identifier">emplace</span></code>
|
||||||
|
initializes the optional in-place by perfect-forwarding the arguments to the
|
||||||
|
constructor of <code class="computeroutput"><span class="identifier">Resource</span></code>. No
|
||||||
|
copy- or move-construction is involved here. <code class="computeroutput"><span class="identifier">Resource</span></code>
|
||||||
|
doesn't even have to be <code class="computeroutput"><span class="identifier">MoveConstructible</span></code>.
|
||||||
|
</p>
|
||||||
|
<div class="note"><table border="0" summary="Note">
|
||||||
|
<tr>
|
||||||
|
<td rowspan="2" align="center" valign="top" width="25"><img alt="[Note]" src="../../../../../doc/src/images/note.png"></td>
|
||||||
|
<th align="left">Note</th>
|
||||||
|
</tr>
|
||||||
|
<tr><td align="left" valign="top"><p>
|
||||||
|
Function <code class="computeroutput"><span class="identifier">emplace</span></code> is only
|
||||||
|
available on compilers that support rvalue references and variadic templates.
|
||||||
|
If your compiler does not support these features and you still need to avoid
|
||||||
|
any move-constructions, use <a class="link" href="tutorial/in_place_factories.html" title="In-Place Factories">In-Place
|
||||||
|
Factories</a>.
|
||||||
|
</p></td></tr>
|
||||||
|
</table></div>
|
||||||
|
<h4>
|
||||||
|
<a name="boost_optional.quick_start.h3"></a>
|
||||||
|
<span class="phrase"><a name="boost_optional.quick_start.bypassing_unnecessary_default_construction"></a></span><a class="link" href="quick_start.html#boost_optional.quick_start.bypassing_unnecessary_default_construction">Bypassing
|
||||||
|
unnecessary default construction</a>
|
||||||
|
</h4>
|
||||||
|
<p>
|
||||||
|
Suppose we have class <code class="computeroutput"><span class="identifier">Date</span></code>,
|
||||||
|
which does not have a default constructor: there is no good candidate for a
|
||||||
|
default date. We have a function that returns two dates in form of a <code class="computeroutput"><span class="identifier">boost</span><span class="special">::</span><span class="identifier">tuple</span></code>:
|
||||||
|
</p>
|
||||||
|
<pre class="programlisting"><span class="identifier">boost</span><span class="special">::</span><span class="identifier">tuple</span><span class="special"><</span><span class="identifier">Date</span><span class="special">,</span> <span class="identifier">Date</span><span class="special">></span> <span class="identifier">getPeriod</span><span class="special">();</span>
|
||||||
|
</pre>
|
||||||
|
<p>
|
||||||
|
In other place we want to use the result of <code class="computeroutput"><span class="identifier">getPeriod</span></code>,
|
||||||
|
but want the two dates to be named: <code class="computeroutput"><span class="identifier">begin</span></code>
|
||||||
|
and <code class="computeroutput"><span class="identifier">end</span></code>. We want to implement
|
||||||
|
something like 'multiple return values':
|
||||||
|
</p>
|
||||||
|
<pre class="programlisting"><span class="identifier">Date</span> <span class="identifier">begin</span><span class="special">,</span> <span class="identifier">end</span><span class="special">;</span> <span class="comment">// Error: no default ctor!</span>
|
||||||
|
<span class="identifier">boost</span><span class="special">::</span><span class="identifier">tie</span><span class="special">(</span><span class="identifier">begin</span><span class="special">,</span> <span class="identifier">end</span><span class="special">)</span> <span class="special">=</span> <span class="identifier">getPeriod</span><span class="special">();</span>
|
||||||
|
</pre>
|
||||||
|
<p>
|
||||||
|
The second line works already, this is the capability of Boost.Tuple library,
|
||||||
|
but the first line won't work. We could set some invented initial dates, but
|
||||||
|
it is confusing and may be an unacceptable cost, given that these values will
|
||||||
|
be overwritten in the next line anyway. This is where <code class="computeroutput"><span class="identifier">optional</span></code>
|
||||||
|
can help:
|
||||||
|
</p>
|
||||||
|
<pre class="programlisting"><span class="identifier">boost</span><span class="special">::</span><span class="identifier">optional</span><span class="special"><</span><span class="identifier">Date</span><span class="special">></span> <span class="identifier">begin</span><span class="special">,</span> <span class="identifier">end</span><span class="special">;</span>
|
||||||
|
<span class="identifier">boost</span><span class="special">::</span><span class="identifier">tie</span><span class="special">(</span><span class="identifier">begin</span><span class="special">,</span> <span class="identifier">end</span><span class="special">)</span> <span class="special">=</span> <span class="identifier">getPeriod</span><span class="special">();</span>
|
||||||
|
</pre>
|
||||||
|
<p>
|
||||||
|
It works because inside <code class="computeroutput"><span class="identifier">boost</span><span class="special">::</span><span class="identifier">tie</span></code> a move-assignment
|
||||||
|
from <code class="computeroutput"><span class="identifier">T</span></code> is invoked on <code class="computeroutput"><span class="identifier">optional</span><span class="special"><</span><span class="identifier">T</span><span class="special">></span></code>, which
|
||||||
|
internally calls a move-constructor of <code class="computeroutput"><span class="identifier">T</span></code>.
|
||||||
|
</p>
|
||||||
|
</div>
|
||||||
|
<table xmlns:rev="http://www.cs.rpi.edu/~gregod/boost/tools/doc/revision" width="100%"><tr>
|
||||||
|
<td align="left"></td>
|
||||||
|
<td align="right"><div class="copyright-footer">Copyright © 2003-2007 Fernando Luis Cacciola Carballal<br>Copyright © 2014 Andrzej Krzemieński<p>
|
||||||
|
Distributed under the Boost Software License, Version 1.0. (See accompanying
|
||||||
|
file LICENSE_1_0.txt or copy at <a href="http://www.boost.org/LICENSE_1_0.txt" target="_top">http://www.boost.org/LICENSE_1_0.txt</a>)
|
||||||
|
</p>
|
||||||
|
</div></td>
|
||||||
|
</tr></table>
|
||||||
|
<hr>
|
||||||
|
<div class="spirit-nav">
|
||||||
|
<a accesskey="p" href="../index.html"><img src="../../../../../doc/src/images/prev.png" alt="Prev"></a><a accesskey="u" href="../index.html"><img src="../../../../../doc/src/images/up.png" alt="Up"></a><a accesskey="h" href="../index.html"><img src="../../../../../doc/src/images/home.png" alt="Home"></a><a accesskey="n" href="../optional/tutorial.html"><img src="../../../../../doc/src/images/next.png" alt="Next"></a>
|
||||||
|
</div>
|
||||||
|
</body>
|
||||||
|
</html>
|
@ -0,0 +1,75 @@
|
|||||||
|
<html>
|
||||||
|
<head>
|
||||||
|
<meta http-equiv="Content-Type" content="text/html; charset=US-ASCII">
|
||||||
|
<title>Bypassing unnecessary default construction</title>
|
||||||
|
<link rel="stylesheet" href="../../../../../../doc/src/boostbook.css" type="text/css">
|
||||||
|
<meta name="generator" content="DocBook XSL Stylesheets V1.78.1">
|
||||||
|
<link rel="home" href="../../index.html" title="Chapter 1. Boost.Optional">
|
||||||
|
<link rel="up" href="../quick_start.html" title="Quick Start">
|
||||||
|
<link rel="prev" href="optional_data_members.html" title="Optional data members">
|
||||||
|
<link rel="next" href="../../optional/tutorial.html" title="Tutorial">
|
||||||
|
</head>
|
||||||
|
<body bgcolor="white" text="black" link="#0000FF" vlink="#840084" alink="#0000FF">
|
||||||
|
<table cellpadding="2" width="100%"><tr>
|
||||||
|
<td valign="top"><img alt="Boost C++ Libraries" width="277" height="86" src="../../../../../../boost.png"></td>
|
||||||
|
<td align="center"><a href="../../../../../../index.html">Home</a></td>
|
||||||
|
<td align="center"><a href="../../../../../../libs/libraries.htm">Libraries</a></td>
|
||||||
|
<td align="center"><a href="http://www.boost.org/users/people.html">People</a></td>
|
||||||
|
<td align="center"><a href="http://www.boost.org/users/faq.html">FAQ</a></td>
|
||||||
|
<td align="center"><a href="../../../../../../more/index.htm">More</a></td>
|
||||||
|
</tr></table>
|
||||||
|
<hr>
|
||||||
|
<div class="spirit-nav">
|
||||||
|
<a accesskey="p" href="optional_data_members.html"><img src="../../../../../../doc/src/images/prev.png" alt="Prev"></a><a accesskey="u" href="../quick_start.html"><img src="../../../../../../doc/src/images/up.png" alt="Up"></a><a accesskey="h" href="../../index.html"><img src="../../../../../../doc/src/images/home.png" alt="Home"></a><a accesskey="n" href="../../optional/tutorial.html"><img src="../../../../../../doc/src/images/next.png" alt="Next"></a>
|
||||||
|
</div>
|
||||||
|
<div class="section">
|
||||||
|
<div class="titlepage"><div><div><h3 class="title">
|
||||||
|
<a name="boost_optional.quick_start.bypassing_unnecessary_default_construction"></a><a class="link" href="bypassing_unnecessary_default_construction.html" title="Bypassing unnecessary default construction">Bypassing
|
||||||
|
unnecessary default construction</a>
|
||||||
|
</h3></div></div></div>
|
||||||
|
<p>
|
||||||
|
Suppose we have class <code class="computeroutput"><span class="identifier">Date</span></code>,
|
||||||
|
which does not have a default constructor: there is no good candidate for
|
||||||
|
a default date. We have a function that returns two dates in form of a <code class="computeroutput"><span class="identifier">boost</span><span class="special">::</span><span class="identifier">tuple</span></code>:
|
||||||
|
</p>
|
||||||
|
<pre class="programlisting"><span class="identifier">boost</span><span class="special">::</span><span class="identifier">tuple</span><span class="special"><</span><span class="identifier">Date</span><span class="special">,</span> <span class="identifier">Date</span><span class="special">></span> <span class="identifier">getPeriod</span><span class="special">();</span>
|
||||||
|
</pre>
|
||||||
|
<p>
|
||||||
|
In other place we want to use the result of <code class="computeroutput"><span class="identifier">getPeriod</span></code>,
|
||||||
|
but want the two dates to be named: <code class="computeroutput"><span class="identifier">begin</span></code>
|
||||||
|
and <code class="computeroutput"><span class="identifier">end</span></code>. We want to implement
|
||||||
|
something like 'multiple return values':
|
||||||
|
</p>
|
||||||
|
<pre class="programlisting"><span class="identifier">Date</span> <span class="identifier">begin</span><span class="special">,</span> <span class="identifier">end</span><span class="special">;</span> <span class="comment">// Error: no default ctor!</span>
|
||||||
|
<span class="identifier">boost</span><span class="special">::</span><span class="identifier">tie</span><span class="special">(</span><span class="identifier">begin</span><span class="special">,</span> <span class="identifier">end</span><span class="special">)</span> <span class="special">=</span> <span class="identifier">getPeriod</span><span class="special">();</span>
|
||||||
|
</pre>
|
||||||
|
<p>
|
||||||
|
The second line works already, this is the capability of Boost.Tuple library,
|
||||||
|
but the first line won't work. We could set some invented initial dates,
|
||||||
|
but it is confusing and may be an unacceptable cost, given that these values
|
||||||
|
will be overwritten in the next line anyway. This is where <code class="computeroutput"><span class="identifier">optional</span></code> can help:
|
||||||
|
</p>
|
||||||
|
<pre class="programlisting"><span class="identifier">boost</span><span class="special">::</span><span class="identifier">optional</span><span class="special"><</span><span class="identifier">Date</span><span class="special">></span> <span class="identifier">begin</span><span class="special">,</span> <span class="identifier">end</span><span class="special">;</span>
|
||||||
|
<span class="identifier">boost</span><span class="special">::</span><span class="identifier">tie</span><span class="special">(</span><span class="identifier">begin</span><span class="special">,</span> <span class="identifier">end</span><span class="special">)</span> <span class="special">=</span> <span class="identifier">getPeriod</span><span class="special">();</span>
|
||||||
|
</pre>
|
||||||
|
<p>
|
||||||
|
It works because inside <code class="computeroutput"><span class="identifier">boost</span><span class="special">::</span><span class="identifier">tie</span></code> a
|
||||||
|
move-assignment from <code class="computeroutput"><span class="identifier">T</span></code> is
|
||||||
|
invoked on <code class="computeroutput"><span class="identifier">optional</span><span class="special"><</span><span class="identifier">T</span><span class="special">></span></code>,
|
||||||
|
which internally calls a move-constructor of <code class="computeroutput"><span class="identifier">T</span></code>.
|
||||||
|
</p>
|
||||||
|
</div>
|
||||||
|
<table xmlns:rev="http://www.cs.rpi.edu/~gregod/boost/tools/doc/revision" width="100%"><tr>
|
||||||
|
<td align="left"></td>
|
||||||
|
<td align="right"><div class="copyright-footer">Copyright © 2003-2007 Fernando Luis Cacciola Carballal<br>Copyright © 2014 Andrzej Krzemieński<p>
|
||||||
|
Distributed under the Boost Software License, Version 1.0. (See accompanying
|
||||||
|
file LICENSE_1_0.txt or copy at <a href="http://www.boost.org/LICENSE_1_0.txt" target="_top">http://www.boost.org/LICENSE_1_0.txt</a>)
|
||||||
|
</p>
|
||||||
|
</div></td>
|
||||||
|
</tr></table>
|
||||||
|
<hr>
|
||||||
|
<div class="spirit-nav">
|
||||||
|
<a accesskey="p" href="optional_data_members.html"><img src="../../../../../../doc/src/images/prev.png" alt="Prev"></a><a accesskey="u" href="../quick_start.html"><img src="../../../../../../doc/src/images/up.png" alt="Up"></a><a accesskey="h" href="../../index.html"><img src="../../../../../../doc/src/images/home.png" alt="Home"></a><a accesskey="n" href="../../optional/tutorial.html"><img src="../../../../../../doc/src/images/next.png" alt="Next"></a>
|
||||||
|
</div>
|
||||||
|
</body>
|
||||||
|
</html>
|
@ -0,0 +1,75 @@
|
|||||||
|
<html>
|
||||||
|
<head>
|
||||||
|
<meta http-equiv="Content-Type" content="text/html; charset=US-ASCII">
|
||||||
|
<title>Optional automatic variables</title>
|
||||||
|
<link rel="stylesheet" href="../../../../../../doc/src/boostbook.css" type="text/css">
|
||||||
|
<meta name="generator" content="DocBook XSL Stylesheets V1.78.1">
|
||||||
|
<link rel="home" href="../../index.html" title="Chapter 1. Boost.Optional">
|
||||||
|
<link rel="up" href="../quick_start.html" title="Quick Start">
|
||||||
|
<link rel="prev" href="optional_return_values.html" title="Optional return values">
|
||||||
|
<link rel="next" href="optional_data_members.html" title="Optional data members">
|
||||||
|
</head>
|
||||||
|
<body bgcolor="white" text="black" link="#0000FF" vlink="#840084" alink="#0000FF">
|
||||||
|
<table cellpadding="2" width="100%"><tr>
|
||||||
|
<td valign="top"><img alt="Boost C++ Libraries" width="277" height="86" src="../../../../../../boost.png"></td>
|
||||||
|
<td align="center"><a href="../../../../../../index.html">Home</a></td>
|
||||||
|
<td align="center"><a href="../../../../../../libs/libraries.htm">Libraries</a></td>
|
||||||
|
<td align="center"><a href="http://www.boost.org/users/people.html">People</a></td>
|
||||||
|
<td align="center"><a href="http://www.boost.org/users/faq.html">FAQ</a></td>
|
||||||
|
<td align="center"><a href="../../../../../../more/index.htm">More</a></td>
|
||||||
|
</tr></table>
|
||||||
|
<hr>
|
||||||
|
<div class="spirit-nav">
|
||||||
|
<a accesskey="p" href="optional_return_values.html"><img src="../../../../../../doc/src/images/prev.png" alt="Prev"></a><a accesskey="u" href="../quick_start.html"><img src="../../../../../../doc/src/images/up.png" alt="Up"></a><a accesskey="h" href="../../index.html"><img src="../../../../../../doc/src/images/home.png" alt="Home"></a><a accesskey="n" href="optional_data_members.html"><img src="../../../../../../doc/src/images/next.png" alt="Next"></a>
|
||||||
|
</div>
|
||||||
|
<div class="section">
|
||||||
|
<div class="titlepage"><div><div><h3 class="title">
|
||||||
|
<a name="boost_optional.quick_start.optional_automatic_variables"></a><a class="link" href="optional_automatic_variables.html" title="Optional automatic variables">Optional
|
||||||
|
automatic variables</a>
|
||||||
|
</h3></div></div></div>
|
||||||
|
<p>
|
||||||
|
We could write function <code class="computeroutput"><span class="identifier">convert</span></code>
|
||||||
|
in a slightly different manner, so that it has a single <code class="computeroutput"><span class="keyword">return</span></code>-statement:
|
||||||
|
</p>
|
||||||
|
<pre class="programlisting"><span class="identifier">boost</span><span class="special">::</span><span class="identifier">optionl</span><span class="special"><</span><span class="keyword">int</span><span class="special">></span> <span class="identifier">convert</span><span class="special">(</span><span class="keyword">const</span> <span class="identifier">std</span><span class="special">::</span><span class="identifier">string</span><span class="special">&</span> <span class="identifier">text</span><span class="special">)</span>
|
||||||
|
<span class="special">{</span>
|
||||||
|
<span class="identifier">boost</span><span class="special">::</span><span class="identifier">optionl</span><span class="special"><</span><span class="keyword">int</span><span class="special">></span> <span class="identifier">ans</span><span class="special">;</span>
|
||||||
|
<span class="identifier">std</span><span class="special">::</span><span class="identifier">stringstream</span> <span class="identifier">s</span><span class="special">(</span><span class="identifier">text</span><span class="special">);</span>
|
||||||
|
<span class="keyword">int</span> <span class="identifier">i</span><span class="special">;</span>
|
||||||
|
<span class="keyword">if</span> <span class="special">((</span><span class="identifier">s</span> <span class="special">>></span> <span class="identifier">i</span><span class="special">)</span> <span class="special">&&</span> <span class="identifier">s</span><span class="special">.</span><span class="identifier">get</span><span class="special">()</span> <span class="special">==</span> <span class="identifier">std</span><span class="special">::</span><span class="identifier">char_traits</span><span class="special"><</span><span class="keyword">char</span><span class="special">>::</span><span class="identifier">eof</span><span class="special">())</span>
|
||||||
|
<span class="identifier">ans</span> <span class="special">=</span> <span class="identifier">i</span><span class="special">;</span>
|
||||||
|
|
||||||
|
<span class="keyword">return</span> <span class="identifier">ans</span><span class="special">;</span>
|
||||||
|
<span class="special">}</span>
|
||||||
|
</pre>
|
||||||
|
<p>
|
||||||
|
The default constructor of <code class="computeroutput"><span class="identifier">optional</span></code>
|
||||||
|
creates an unitialized optional object. Unlike with <code class="computeroutput"><span class="keyword">int</span></code>s
|
||||||
|
you cannot have an <code class="computeroutput"><span class="identifier">optional</span><span class="special"><</span><span class="keyword">int</span><span class="special">></span></code>
|
||||||
|
in an indeterminate state. Its state is always well defined. Instruction
|
||||||
|
<code class="computeroutput"><span class="identifier">ans</span> <span class="special">=</span>
|
||||||
|
<span class="identifier">i</span></code> initializes the optional object.
|
||||||
|
It uses the assignment from <code class="computeroutput"><span class="keyword">int</span></code>.
|
||||||
|
In general, for <code class="computeroutput"><span class="identifier">optional</span><span class="special"><</span><span class="identifier">T</span><span class="special">></span></code>,
|
||||||
|
when an assignment from <code class="computeroutput"><span class="identifier">T</span></code>
|
||||||
|
is invoked, it can do two things. If the optional object is not initialized
|
||||||
|
our case here), it initializes it with <code class="computeroutput"><span class="identifier">T</span></code>'s
|
||||||
|
copy constructor. If the optional object is already initialized, it assigns
|
||||||
|
the new value to it using <code class="computeroutput"><span class="identifier">T</span></code>'s
|
||||||
|
copy assignment.
|
||||||
|
</p>
|
||||||
|
</div>
|
||||||
|
<table xmlns:rev="http://www.cs.rpi.edu/~gregod/boost/tools/doc/revision" width="100%"><tr>
|
||||||
|
<td align="left"></td>
|
||||||
|
<td align="right"><div class="copyright-footer">Copyright © 2003-2007 Fernando Luis Cacciola Carballal<br>Copyright © 2014 Andrzej Krzemieński<p>
|
||||||
|
Distributed under the Boost Software License, Version 1.0. (See accompanying
|
||||||
|
file LICENSE_1_0.txt or copy at <a href="http://www.boost.org/LICENSE_1_0.txt" target="_top">http://www.boost.org/LICENSE_1_0.txt</a>)
|
||||||
|
</p>
|
||||||
|
</div></td>
|
||||||
|
</tr></table>
|
||||||
|
<hr>
|
||||||
|
<div class="spirit-nav">
|
||||||
|
<a accesskey="p" href="optional_return_values.html"><img src="../../../../../../doc/src/images/prev.png" alt="Prev"></a><a accesskey="u" href="../quick_start.html"><img src="../../../../../../doc/src/images/up.png" alt="Up"></a><a accesskey="h" href="../../index.html"><img src="../../../../../../doc/src/images/home.png" alt="Home"></a><a accesskey="n" href="optional_data_members.html"><img src="../../../../../../doc/src/images/next.png" alt="Next"></a>
|
||||||
|
</div>
|
||||||
|
</body>
|
||||||
|
</html>
|
@ -0,0 +1,92 @@
|
|||||||
|
<html>
|
||||||
|
<head>
|
||||||
|
<meta http-equiv="Content-Type" content="text/html; charset=US-ASCII">
|
||||||
|
<title>Optional data members</title>
|
||||||
|
<link rel="stylesheet" href="../../../../../../doc/src/boostbook.css" type="text/css">
|
||||||
|
<meta name="generator" content="DocBook XSL Stylesheets V1.78.1">
|
||||||
|
<link rel="home" href="../../index.html" title="Chapter 1. Boost.Optional">
|
||||||
|
<link rel="up" href="../quick_start.html" title="Quick Start">
|
||||||
|
<link rel="prev" href="optional_automatic_variables.html" title="Optional automatic variables">
|
||||||
|
<link rel="next" href="bypassing_unnecessary_default_construction.html" title="Bypassing unnecessary default construction">
|
||||||
|
</head>
|
||||||
|
<body bgcolor="white" text="black" link="#0000FF" vlink="#840084" alink="#0000FF">
|
||||||
|
<table cellpadding="2" width="100%"><tr>
|
||||||
|
<td valign="top"><img alt="Boost C++ Libraries" width="277" height="86" src="../../../../../../boost.png"></td>
|
||||||
|
<td align="center"><a href="../../../../../../index.html">Home</a></td>
|
||||||
|
<td align="center"><a href="../../../../../../libs/libraries.htm">Libraries</a></td>
|
||||||
|
<td align="center"><a href="http://www.boost.org/users/people.html">People</a></td>
|
||||||
|
<td align="center"><a href="http://www.boost.org/users/faq.html">FAQ</a></td>
|
||||||
|
<td align="center"><a href="../../../../../../more/index.htm">More</a></td>
|
||||||
|
</tr></table>
|
||||||
|
<hr>
|
||||||
|
<div class="spirit-nav">
|
||||||
|
<a accesskey="p" href="optional_automatic_variables.html"><img src="../../../../../../doc/src/images/prev.png" alt="Prev"></a><a accesskey="u" href="../quick_start.html"><img src="../../../../../../doc/src/images/up.png" alt="Up"></a><a accesskey="h" href="../../index.html"><img src="../../../../../../doc/src/images/home.png" alt="Home"></a><a accesskey="n" href="bypassing_unnecessary_default_construction.html"><img src="../../../../../../doc/src/images/next.png" alt="Next"></a>
|
||||||
|
</div>
|
||||||
|
<div class="section">
|
||||||
|
<div class="titlepage"><div><div><h3 class="title">
|
||||||
|
<a name="boost_optional.quick_start.optional_data_members"></a><a class="link" href="optional_data_members.html" title="Optional data members">Optional
|
||||||
|
data members</a>
|
||||||
|
</h3></div></div></div>
|
||||||
|
<p>
|
||||||
|
Suppose we want to implement a <span class="emphasis"><em>lazy load</em></span> optimization.
|
||||||
|
This is because we do not want to perform an expensive initialization of
|
||||||
|
our <code class="computeroutput"><span class="identifier">Resource</span></code> until (if at
|
||||||
|
all) it is really used. We can do it this way:
|
||||||
|
</p>
|
||||||
|
<pre class="programlisting"><span class="keyword">class</span> <span class="identifier">Widget</span>
|
||||||
|
<span class="special">{</span>
|
||||||
|
<span class="identifier">boost</span><span class="special">::</span><span class="identifier">optional</span><span class="special"><</span><span class="identifier">Resource</span><span class="special">></span> <span class="identifier">resource_</span><span class="special">;</span>
|
||||||
|
|
||||||
|
<span class="keyword">public</span><span class="special">:</span>
|
||||||
|
<span class="identifier">Widget</span><span class="special">()</span> <span class="special">{}</span>
|
||||||
|
|
||||||
|
<span class="identifier">Resource</span><span class="special">&</span> <span class="identifier">getResource</span><span class="special">()</span> <span class="comment">// not thread-safe</span>
|
||||||
|
<span class="special">{</span>
|
||||||
|
<span class="keyword">if</span> <span class="special">(</span><span class="identifier">resource_</span> <span class="special">==</span> <span class="identifier">boost</span><span class="special">::</span><span class="identifier">none</span><span class="special">)</span>
|
||||||
|
<span class="identifier">resource_</span><span class="special">.</span><span class="identifier">emplace</span><span class="special">(</span><span class="string">"resource"</span><span class="special">,</span> <span class="string">"arguments"</span><span class="special">);</span>
|
||||||
|
|
||||||
|
<span class="keyword">return</span> <span class="special">*</span><span class="identifier">resource_</span><span class="special">;</span>
|
||||||
|
<span class="special">}</span>
|
||||||
|
<span class="special">};</span>
|
||||||
|
</pre>
|
||||||
|
<p>
|
||||||
|
<code class="computeroutput"><span class="identifier">optional</span></code>'s default constructor
|
||||||
|
creates an uninitialized optional. No call to <code class="computeroutput"><span class="identifier">Resource</span></code>'s
|
||||||
|
default constructor is attempted. <code class="computeroutput"><span class="identifier">Resource</span></code>
|
||||||
|
doesn't have to be <a href="http://www.sgi.com/tech/stl/DefaultConstructible.html" target="_top">Default
|
||||||
|
Constructible</a>. In function <code class="computeroutput"><span class="identifier">getResource</span></code>
|
||||||
|
we first check if <code class="computeroutput"><span class="identifier">resource_</span></code>
|
||||||
|
is initialized. This time we do not use the contextual conversion to <code class="computeroutput"><span class="keyword">bool</span></code>, but a comparison with <code class="computeroutput"><span class="identifier">boost</span><span class="special">::</span><span class="identifier">none</span></code>. These two ways are equivalent. Function
|
||||||
|
<code class="computeroutput"><span class="identifier">emplace</span></code> initializes the optional
|
||||||
|
in-place by perfect-forwarding the arguments to the constructor of <code class="computeroutput"><span class="identifier">Resource</span></code>. No copy- or move-construction
|
||||||
|
is involved here. <code class="computeroutput"><span class="identifier">Resource</span></code>
|
||||||
|
doesn't even have to be <code class="computeroutput"><span class="identifier">MoveConstructible</span></code>.
|
||||||
|
</p>
|
||||||
|
<div class="note"><table border="0" summary="Note">
|
||||||
|
<tr>
|
||||||
|
<td rowspan="2" align="center" valign="top" width="25"><img alt="[Note]" src="../../../../../../doc/src/images/note.png"></td>
|
||||||
|
<th align="left">Note</th>
|
||||||
|
</tr>
|
||||||
|
<tr><td align="left" valign="top"><p>
|
||||||
|
Function <code class="computeroutput"><span class="identifier">emplace</span></code> is only
|
||||||
|
available on compilers that support rvalue references and variadic templates.
|
||||||
|
If your compiler does not support these features and you still need to
|
||||||
|
avoid any move-constructions, use <a class="link" href="../tutorial/in_place_factories.html" title="In-Place Factories">In-Place
|
||||||
|
Factories</a>.
|
||||||
|
</p></td></tr>
|
||||||
|
</table></div>
|
||||||
|
</div>
|
||||||
|
<table xmlns:rev="http://www.cs.rpi.edu/~gregod/boost/tools/doc/revision" width="100%"><tr>
|
||||||
|
<td align="left"></td>
|
||||||
|
<td align="right"><div class="copyright-footer">Copyright © 2003-2007 Fernando Luis Cacciola Carballal<br>Copyright © 2014 Andrzej Krzemieński<p>
|
||||||
|
Distributed under the Boost Software License, Version 1.0. (See accompanying
|
||||||
|
file LICENSE_1_0.txt or copy at <a href="http://www.boost.org/LICENSE_1_0.txt" target="_top">http://www.boost.org/LICENSE_1_0.txt</a>)
|
||||||
|
</p>
|
||||||
|
</div></td>
|
||||||
|
</tr></table>
|
||||||
|
<hr>
|
||||||
|
<div class="spirit-nav">
|
||||||
|
<a accesskey="p" href="optional_automatic_variables.html"><img src="../../../../../../doc/src/images/prev.png" alt="Prev"></a><a accesskey="u" href="../quick_start.html"><img src="../../../../../../doc/src/images/up.png" alt="Up"></a><a accesskey="h" href="../../index.html"><img src="../../../../../../doc/src/images/home.png" alt="Home"></a><a accesskey="n" href="bypassing_unnecessary_default_construction.html"><img src="../../../../../../doc/src/images/next.png" alt="Next"></a>
|
||||||
|
</div>
|
||||||
|
</body>
|
||||||
|
</html>
|
135
doc/html/boost_optional/quick_start/optional_return_values.html
Normal file
135
doc/html/boost_optional/quick_start/optional_return_values.html
Normal file
@ -0,0 +1,135 @@
|
|||||||
|
<html>
|
||||||
|
<head>
|
||||||
|
<meta http-equiv="Content-Type" content="text/html; charset=US-ASCII">
|
||||||
|
<title>Optional return values</title>
|
||||||
|
<link rel="stylesheet" href="../../../../../../doc/src/boostbook.css" type="text/css">
|
||||||
|
<meta name="generator" content="DocBook XSL Stylesheets V1.78.1">
|
||||||
|
<link rel="home" href="../../index.html" title="Chapter 1. Boost.Optional">
|
||||||
|
<link rel="up" href="../quick_start.html" title="Quick Start">
|
||||||
|
<link rel="prev" href="../quick_start.html" title="Quick Start">
|
||||||
|
<link rel="next" href="optional_automatic_variables.html" title="Optional automatic variables">
|
||||||
|
</head>
|
||||||
|
<body bgcolor="white" text="black" link="#0000FF" vlink="#840084" alink="#0000FF">
|
||||||
|
<table cellpadding="2" width="100%"><tr>
|
||||||
|
<td valign="top"><img alt="Boost C++ Libraries" width="277" height="86" src="../../../../../../boost.png"></td>
|
||||||
|
<td align="center"><a href="../../../../../../index.html">Home</a></td>
|
||||||
|
<td align="center"><a href="../../../../../../libs/libraries.htm">Libraries</a></td>
|
||||||
|
<td align="center"><a href="http://www.boost.org/users/people.html">People</a></td>
|
||||||
|
<td align="center"><a href="http://www.boost.org/users/faq.html">FAQ</a></td>
|
||||||
|
<td align="center"><a href="../../../../../../more/index.htm">More</a></td>
|
||||||
|
</tr></table>
|
||||||
|
<hr>
|
||||||
|
<div class="spirit-nav">
|
||||||
|
<a accesskey="p" href="../quick_start.html"><img src="../../../../../../doc/src/images/prev.png" alt="Prev"></a><a accesskey="u" href="../quick_start.html"><img src="../../../../../../doc/src/images/up.png" alt="Up"></a><a accesskey="h" href="../../index.html"><img src="../../../../../../doc/src/images/home.png" alt="Home"></a><a accesskey="n" href="optional_automatic_variables.html"><img src="../../../../../../doc/src/images/next.png" alt="Next"></a>
|
||||||
|
</div>
|
||||||
|
<div class="section">
|
||||||
|
<div class="titlepage"><div><div><h3 class="title">
|
||||||
|
<a name="boost_optional.quick_start.optional_return_values"></a><a class="link" href="optional_return_values.html" title="Optional return values">Optional
|
||||||
|
return values</a>
|
||||||
|
</h3></div></div></div>
|
||||||
|
<p>
|
||||||
|
Let's write and use a converter function that converts an a <code class="computeroutput"><span class="identifier">std</span><span class="special">::</span><span class="identifier">string</span></code>
|
||||||
|
to an <code class="computeroutput"><span class="keyword">int</span></code>. It is possible that
|
||||||
|
for a given string (e.g. <code class="computeroutput"><span class="string">"cat"</span></code>)
|
||||||
|
there exist no value of type <code class="computeroutput"><span class="keyword">int</span></code>
|
||||||
|
capable of representing the conversion result. We do not consider such situation
|
||||||
|
an error. We expect that the converter can be used only to check if the conversion
|
||||||
|
is possible. A natural signature for this function can be:
|
||||||
|
</p>
|
||||||
|
<pre class="programlisting"><span class="preprocessor">#include</span> <span class="special"><</span><span class="identifier">boost</span><span class="special">/</span><span class="identifier">optional</span><span class="special">.</span><span class="identifier">hpp</span><span class="special">></span>
|
||||||
|
<span class="identifier">boost</span><span class="special">::</span><span class="identifier">optionl</span><span class="special"><</span><span class="keyword">int</span><span class="special">></span> <span class="identifier">convert</span><span class="special">(</span><span class="keyword">const</span> <span class="identifier">std</span><span class="special">::</span><span class="identifier">string</span><span class="special">&</span> <span class="identifier">text</span><span class="special">);</span>
|
||||||
|
</pre>
|
||||||
|
<p>
|
||||||
|
All necessary functionality can be included with one header <code class="computeroutput"><span class="special"><</span><span class="identifier">boost</span><span class="special">/</span><span class="identifier">optional</span><span class="special">.</span><span class="identifier">hpp</span><span class="special">></span></code>.
|
||||||
|
The above function signature means that the function can either return a
|
||||||
|
value of type <code class="computeroutput"><span class="keyword">int</span></code> or a flag
|
||||||
|
indicating that no value of <code class="computeroutput"><span class="keyword">int</span></code>
|
||||||
|
is available. This does not indicate an error. It is like one additional
|
||||||
|
value of <code class="computeroutput"><span class="keyword">int</span></code>. This is how we
|
||||||
|
can use our function:
|
||||||
|
</p>
|
||||||
|
<pre class="programlisting"><span class="keyword">const</span> <span class="identifier">std</span><span class="special">::</span><span class="identifier">string</span><span class="special">&</span> <span class="identifier">text</span> <span class="special">=</span> <span class="comment">/*... */</span><span class="special">;</span>
|
||||||
|
<span class="identifier">boost</span><span class="special">::</span><span class="identifier">optionl</span><span class="special"><</span><span class="keyword">int</span><span class="special">></span> <span class="identifier">oi</span> <span class="special">=</span> <span class="identifier">convert</span><span class="special">(</span><span class="identifier">text</span><span class="special">);</span> <span class="comment">// move-construct</span>
|
||||||
|
<span class="keyword">if</span> <span class="special">(</span><span class="identifier">oi</span><span class="special">)</span> <span class="comment">// contextual conversion to bool</span>
|
||||||
|
<span class="keyword">int</span> <span class="identifier">i</span> <span class="special">=</span> <span class="special">*</span><span class="identifier">oi</span><span class="special">;</span> <span class="comment">// operator*</span>
|
||||||
|
</pre>
|
||||||
|
<p>
|
||||||
|
In order to test if <code class="computeroutput"><span class="identifier">optional</span></code>
|
||||||
|
contains a value, we use the contextual conversion to type <code class="computeroutput"><span class="keyword">bool</span></code>. Because of this we can combine the initialization
|
||||||
|
of the optional object and the test into one instruction:
|
||||||
|
</p>
|
||||||
|
<pre class="programlisting"><span class="keyword">if</span> <span class="special">(</span><span class="identifier">boost</span><span class="special">::</span><span class="identifier">optionl</span><span class="special"><</span><span class="keyword">int</span><span class="special">></span> <span class="identifier">oi</span> <span class="special">=</span> <span class="identifier">convert</span><span class="special">(</span><span class="identifier">text</span><span class="special">))</span>
|
||||||
|
<span class="keyword">int</span> <span class="identifier">i</span> <span class="special">=</span> <span class="special">*</span><span class="identifier">oi</span><span class="special">;</span>
|
||||||
|
</pre>
|
||||||
|
<p>
|
||||||
|
We extract the contained value with <code class="computeroutput"><span class="keyword">operator</span><span class="special">*</span></code> (and with <code class="computeroutput"><span class="keyword">operator</span><span class="special">-></span></code> where it makes sense). An attempt to
|
||||||
|
extract the contained value of an uninitialized optional object is an <span class="emphasis"><em>undefined
|
||||||
|
behaviour</em></span> (UB). This implementation guards the call with <code class="computeroutput"><span class="identifier">BOOST_ASSERT</span></code>. Therefore you should be sure
|
||||||
|
that the contained value is there before extracting. For instance, the following
|
||||||
|
code is reasonably UB-safe:
|
||||||
|
</p>
|
||||||
|
<pre class="programlisting"><span class="keyword">int</span> <span class="identifier">i</span> <span class="special">=</span> <span class="special">*</span><span class="identifier">convert</span><span class="special">(</span><span class="string">"100"</span><span class="special">);</span>
|
||||||
|
</pre>
|
||||||
|
<p>
|
||||||
|
This is because we know that string value <code class="computeroutput"><span class="string">"100"</span></code>
|
||||||
|
converts to a valid value of <code class="computeroutput"><span class="keyword">int</span></code>.
|
||||||
|
If you do not like this potential UB, you can use an alternative way of extracting
|
||||||
|
the contained value:
|
||||||
|
</p>
|
||||||
|
<pre class="programlisting"><span class="keyword">try</span> <span class="special">{</span>
|
||||||
|
<span class="keyword">int</span> <span class="identifier">j</span> <span class="special">=</span> <span class="identifier">convert</span><span class="special">(</span><span class="identifier">text</span><span class="special">).</span><span class="identifier">value</span><span class="special">();</span>
|
||||||
|
<span class="special">}</span>
|
||||||
|
<span class="keyword">catch</span> <span class="special">(</span><span class="keyword">const</span> <span class="identifier">boost</span><span class="special">::</span><span class="identifier">bad_optional_access</span><span class="special">&)</span> <span class="special">{</span>
|
||||||
|
<span class="comment">// deal with it</span>
|
||||||
|
<span class="special">}</span>
|
||||||
|
</pre>
|
||||||
|
<p>
|
||||||
|
This version throws an exception upon an attempt to access a non-existent
|
||||||
|
contained value. If your way of dealing with the missing value is to use
|
||||||
|
some default, like <code class="computeroutput"><span class="number">0</span></code>, there exists
|
||||||
|
a yet another alternative:
|
||||||
|
</p>
|
||||||
|
<pre class="programlisting"><span class="keyword">int</span> <span class="identifier">k</span> <span class="special">=</span> <span class="identifier">convert</span><span class="special">(</span><span class="identifier">text</span><span class="special">).</span><span class="identifier">value_or</span><span class="special">(</span><span class="number">0</span><span class="special">);</span>
|
||||||
|
</pre>
|
||||||
|
<p>
|
||||||
|
This uses the <code class="computeroutput"><span class="identifier">atoi</span></code>-like approach
|
||||||
|
to conversions: if <code class="computeroutput"><span class="identifier">text</span></code> does
|
||||||
|
not represent an integral number just return <code class="computeroutput"><span class="number">0</span></code>.
|
||||||
|
Now, let's consider how function <code class="computeroutput"><span class="identifier">convert</span></code>
|
||||||
|
can be implemented.
|
||||||
|
</p>
|
||||||
|
<pre class="programlisting"><span class="identifier">boost</span><span class="special">::</span><span class="identifier">optionl</span><span class="special"><</span><span class="keyword">int</span><span class="special">></span> <span class="identifier">convert</span><span class="special">(</span><span class="keyword">const</span> <span class="identifier">std</span><span class="special">::</span><span class="identifier">string</span><span class="special">&</span> <span class="identifier">text</span><span class="special">)</span>
|
||||||
|
<span class="special">{</span>
|
||||||
|
<span class="identifier">std</span><span class="special">::</span><span class="identifier">stringstream</span> <span class="identifier">s</span><span class="special">(</span><span class="identifier">text</span><span class="special">);</span>
|
||||||
|
<span class="keyword">int</span> <span class="identifier">i</span><span class="special">;</span>
|
||||||
|
<span class="keyword">if</span> <span class="special">((</span><span class="identifier">s</span> <span class="special">>></span> <span class="identifier">i</span><span class="special">)</span> <span class="special">&&</span> <span class="identifier">s</span><span class="special">.</span><span class="identifier">get</span><span class="special">()</span> <span class="special">==</span> <span class="identifier">std</span><span class="special">::</span><span class="identifier">char_traits</span><span class="special"><</span><span class="keyword">char</span><span class="special">>::</span><span class="identifier">eof</span><span class="special">())</span>
|
||||||
|
<span class="keyword">return</span> <span class="identifier">i</span><span class="special">;</span>
|
||||||
|
<span class="keyword">else</span>
|
||||||
|
<span class="keyword">return</span> <span class="identifier">boost</span><span class="special">::</span><span class="identifier">none</span><span class="special">;</span>
|
||||||
|
<span class="special">}</span>
|
||||||
|
</pre>
|
||||||
|
<p>
|
||||||
|
Observe the two return statements. <code class="computeroutput"><span class="keyword">return</span>
|
||||||
|
<span class="identifier">i</span></code> uses the converting constructor
|
||||||
|
that can create <code class="computeroutput"><span class="identifier">optional</span><span class="special"><</span><span class="identifier">T</span><span class="special">></span></code>
|
||||||
|
from <code class="computeroutput"><span class="identifier">T</span></code>. Thus constructed
|
||||||
|
optional object is initialized and its value is a copy of <code class="computeroutput"><span class="identifier">i</span></code>.
|
||||||
|
The other return statement uses another converting constructor from a special
|
||||||
|
tag <code class="computeroutput"><span class="identifier">boost</span><span class="special">::</span><span class="identifier">none</span></code>. It is used to indicate that we want
|
||||||
|
to create an uninitialized optional object.
|
||||||
|
</p>
|
||||||
|
</div>
|
||||||
|
<table xmlns:rev="http://www.cs.rpi.edu/~gregod/boost/tools/doc/revision" width="100%"><tr>
|
||||||
|
<td align="left"></td>
|
||||||
|
<td align="right"><div class="copyright-footer">Copyright © 2003-2007 Fernando Luis Cacciola Carballal<br>Copyright © 2014 Andrzej Krzemieński<p>
|
||||||
|
Distributed under the Boost Software License, Version 1.0. (See accompanying
|
||||||
|
file LICENSE_1_0.txt or copy at <a href="http://www.boost.org/LICENSE_1_0.txt" target="_top">http://www.boost.org/LICENSE_1_0.txt</a>)
|
||||||
|
</p>
|
||||||
|
</div></td>
|
||||||
|
</tr></table>
|
||||||
|
<hr>
|
||||||
|
<div class="spirit-nav">
|
||||||
|
<a accesskey="p" href="../quick_start.html"><img src="../../../../../../doc/src/images/prev.png" alt="Prev"></a><a accesskey="u" href="../quick_start.html"><img src="../../../../../../doc/src/images/up.png" alt="Up"></a><a accesskey="h" href="../../index.html"><img src="../../../../../../doc/src/images/home.png" alt="Home"></a><a accesskey="n" href="optional_automatic_variables.html"><img src="../../../../../../doc/src/images/next.png" alt="Next"></a>
|
||||||
|
</div>
|
||||||
|
</body>
|
||||||
|
</html>
|
1963
doc/html/boost_optional/reference/detailed_semantics.html
Normal file
1963
doc/html/boost_optional/reference/detailed_semantics.html
Normal file
File diff suppressed because it is too large
Load Diff
174
doc/html/boost_optional/reference/synopsis.html
Normal file
174
doc/html/boost_optional/reference/synopsis.html
Normal file
@ -0,0 +1,174 @@
|
|||||||
|
<html>
|
||||||
|
<head>
|
||||||
|
<meta http-equiv="Content-Type" content="text/html; charset=US-ASCII">
|
||||||
|
<title>Synopsis</title>
|
||||||
|
<link rel="stylesheet" href="../../../../../../doc/src/boostbook.css" type="text/css">
|
||||||
|
<meta name="generator" content="DocBook XSL Stylesheets V1.78.1">
|
||||||
|
<link rel="home" href="../../index.html" title="Chapter 1. Boost.Optional">
|
||||||
|
<link rel="up" href="../../optional/reference.html" title="Reference">
|
||||||
|
<link rel="prev" href="../../optional/reference.html" title="Reference">
|
||||||
|
<link rel="next" href="detailed_semantics.html" title="Detailed Semantics">
|
||||||
|
</head>
|
||||||
|
<body bgcolor="white" text="black" link="#0000FF" vlink="#840084" alink="#0000FF">
|
||||||
|
<table cellpadding="2" width="100%"><tr>
|
||||||
|
<td valign="top"><img alt="Boost C++ Libraries" width="277" height="86" src="../../../../../../boost.png"></td>
|
||||||
|
<td align="center"><a href="../../../../../../index.html">Home</a></td>
|
||||||
|
<td align="center"><a href="../../../../../../libs/libraries.htm">Libraries</a></td>
|
||||||
|
<td align="center"><a href="http://www.boost.org/users/people.html">People</a></td>
|
||||||
|
<td align="center"><a href="http://www.boost.org/users/faq.html">FAQ</a></td>
|
||||||
|
<td align="center"><a href="../../../../../../more/index.htm">More</a></td>
|
||||||
|
</tr></table>
|
||||||
|
<hr>
|
||||||
|
<div class="spirit-nav">
|
||||||
|
<a accesskey="p" href="../../optional/reference.html"><img src="../../../../../../doc/src/images/prev.png" alt="Prev"></a><a accesskey="u" href="../../optional/reference.html"><img src="../../../../../../doc/src/images/up.png" alt="Up"></a><a accesskey="h" href="../../index.html"><img src="../../../../../../doc/src/images/home.png" alt="Home"></a><a accesskey="n" href="detailed_semantics.html"><img src="../../../../../../doc/src/images/next.png" alt="Next"></a>
|
||||||
|
</div>
|
||||||
|
<div class="section">
|
||||||
|
<div class="titlepage"><div><div><h3 class="title">
|
||||||
|
<a name="boost_optional.reference.synopsis"></a><a class="link" href="synopsis.html" title="Synopsis">Synopsis</a>
|
||||||
|
</h3></div></div></div>
|
||||||
|
<pre class="programlisting"><code class="computeroutput"><span class="comment">// In Header: <</span></code><a href="../../../../../../boost/optional/optional.hpp" target="_top">boost/optional/optional.hpp</a><span class="comment">></span>
|
||||||
|
|
||||||
|
<span class="keyword">namespace</span> <span class="identifier">boost</span> <span class="special">{</span>
|
||||||
|
|
||||||
|
<span class="keyword">template</span><span class="special"><</span><span class="keyword">class</span> <span class="identifier">T</span><span class="special">></span>
|
||||||
|
<span class="keyword">class</span> <span class="identifier">optional</span>
|
||||||
|
<span class="special">{</span>
|
||||||
|
<span class="keyword">public</span> <span class="special">:</span>
|
||||||
|
|
||||||
|
<span class="comment">// (If T is of reference type, the parameters and results by reference are by value)</span>
|
||||||
|
|
||||||
|
<span class="identifier">optional</span> <span class="special">()</span> <span class="keyword">noexcept</span> <span class="special">;</span> <a class="link" href="detailed_semantics.html#reference_optional_constructor"><span class="inlinemediaobject"><img src="../../images/callouts/R.png" alt="R"></span></a>
|
||||||
|
|
||||||
|
<span class="identifier">optional</span> <span class="special">(</span> <span class="identifier">none_t</span> <span class="special">)</span> <span class="keyword">noexcept</span> <span class="special">;</span> <a class="link" href="detailed_semantics.html#reference_optional_constructor_none_t"><span class="inlinemediaobject"><img src="../../images/callouts/R.png" alt="R"></span></a>
|
||||||
|
|
||||||
|
<span class="identifier">optional</span> <span class="special">(</span> <span class="identifier">T</span> <span class="keyword">const</span><span class="special">&</span> <span class="identifier">v</span> <span class="special">)</span> <span class="special">;</span> <a class="link" href="detailed_semantics.html#reference_optional_constructor_value"><span class="inlinemediaobject"><img src="../../images/callouts/R.png" alt="R"></span></a>
|
||||||
|
|
||||||
|
<span class="identifier">optional</span> <span class="special">(</span> <span class="identifier">T</span><span class="special">&&</span> <span class="identifier">v</span> <span class="special">)</span> <span class="special">;</span> <a class="link" href="detailed_semantics.html#reference_optional_constructor_move_value"><span class="inlinemediaobject"><img src="../../images/callouts/R.png" alt="R"></span></a>
|
||||||
|
|
||||||
|
<span class="comment">// [new in 1.34]</span>
|
||||||
|
<span class="identifier">optional</span> <span class="special">(</span> <span class="keyword">bool</span> <span class="identifier">condition</span><span class="special">,</span> <span class="identifier">T</span> <span class="keyword">const</span><span class="special">&</span> <span class="identifier">v</span> <span class="special">)</span> <span class="special">;</span> <a class="link" href="detailed_semantics.html#reference_optional_constructor_bool_value"><span class="inlinemediaobject"><img src="../../images/callouts/R.png" alt="R"></span></a>
|
||||||
|
|
||||||
|
<span class="identifier">optional</span> <span class="special">(</span> <span class="identifier">optional</span> <span class="keyword">const</span><span class="special">&</span> <span class="identifier">rhs</span> <span class="special">)</span> <span class="special">;</span> <a class="link" href="detailed_semantics.html#reference_optional_constructor_optional"><span class="inlinemediaobject"><img src="../../images/callouts/R.png" alt="R"></span></a>
|
||||||
|
|
||||||
|
<span class="identifier">optional</span> <span class="special">(</span> <span class="identifier">optional</span><span class="special">&&</span> <span class="identifier">rhs</span> <span class="special">)</span> <span class="keyword">noexcept</span><span class="special">(</span><span class="emphasis"><em>see below</em></span><span class="special">)</span> <span class="special">;</span> <a class="link" href="detailed_semantics.html#reference_optional_move_constructor_optional"><span class="inlinemediaobject"><img src="../../images/callouts/R.png" alt="R"></span></a>
|
||||||
|
|
||||||
|
<span class="keyword">template</span><span class="special"><</span><span class="keyword">class</span> <span class="identifier">U</span><span class="special">></span> <span class="keyword">explicit</span> <span class="identifier">optional</span> <span class="special">(</span> <span class="identifier">optional</span><span class="special"><</span><span class="identifier">U</span><span class="special">></span> <span class="keyword">const</span><span class="special">&</span> <span class="identifier">rhs</span> <span class="special">)</span> <span class="special">;</span> <a class="link" href="detailed_semantics.html#reference_optional_constructor_other_optional"><span class="inlinemediaobject"><img src="../../images/callouts/R.png" alt="R"></span></a>
|
||||||
|
|
||||||
|
<span class="keyword">template</span><span class="special"><</span><span class="keyword">class</span> <span class="identifier">U</span><span class="special">></span> <span class="keyword">explicit</span> <span class="identifier">optional</span> <span class="special">(</span> <span class="identifier">optional</span><span class="special"><</span><span class="identifier">U</span><span class="special">>&&</span> <span class="identifier">rhs</span> <span class="special">)</span> <span class="special">;</span> <a class="link" href="detailed_semantics.html#reference_optional_move_constructor_other_optional"><span class="inlinemediaobject"><img src="../../images/callouts/R.png" alt="R"></span></a>
|
||||||
|
|
||||||
|
<span class="keyword">template</span><span class="special"><</span><span class="keyword">class</span> <span class="identifier">InPlaceFactory</span><span class="special">></span> <span class="keyword">explicit</span> <span class="identifier">optional</span> <span class="special">(</span> <span class="identifier">InPlaceFactory</span> <span class="keyword">const</span><span class="special">&</span> <span class="identifier">f</span> <span class="special">)</span> <span class="special">;</span> <a class="link" href="detailed_semantics.html#reference_optional_constructor_factory"><span class="inlinemediaobject"><img src="../../images/callouts/R.png" alt="R"></span></a>
|
||||||
|
|
||||||
|
<span class="keyword">template</span><span class="special"><</span><span class="keyword">class</span> <span class="identifier">TypedInPlaceFactory</span><span class="special">></span> <span class="keyword">explicit</span> <span class="identifier">optional</span> <span class="special">(</span> <span class="identifier">TypedInPlaceFactory</span> <span class="keyword">const</span><span class="special">&</span> <span class="identifier">f</span> <span class="special">)</span> <span class="special">;</span> <a class="link" href="detailed_semantics.html#reference_optional_constructor_factory"><span class="inlinemediaobject"><img src="../../images/callouts/R.png" alt="R"></span></a>
|
||||||
|
|
||||||
|
<span class="identifier">optional</span><span class="special">&</span> <span class="keyword">operator</span> <span class="special">=</span> <span class="special">(</span> <span class="identifier">none_t</span> <span class="special">)</span> <span class="keyword">noexcept</span> <span class="special">;</span> <a class="link" href="detailed_semantics.html#reference_optional_operator_equal_none_t"><span class="inlinemediaobject"><img src="../../images/callouts/R.png" alt="R"></span></a>
|
||||||
|
|
||||||
|
<span class="identifier">optional</span><span class="special">&</span> <span class="keyword">operator</span> <span class="special">=</span> <span class="special">(</span> <span class="identifier">T</span> <span class="keyword">const</span><span class="special">&</span> <span class="identifier">v</span> <span class="special">)</span> <span class="special">;</span> <a class="link" href="detailed_semantics.html#reference_optional_operator_equal_value"><span class="inlinemediaobject"><img src="../../images/callouts/R.png" alt="R"></span></a>
|
||||||
|
|
||||||
|
<span class="identifier">optional</span><span class="special">&</span> <span class="keyword">operator</span> <span class="special">=</span> <span class="special">(</span> <span class="identifier">T</span><span class="special">&&</span> <span class="identifier">v</span> <span class="special">)</span> <span class="special">;</span> <a class="link" href="detailed_semantics.html#reference_optional_operator_move_equal_value"><span class="inlinemediaobject"><img src="../../images/callouts/R.png" alt="R"></span></a>
|
||||||
|
|
||||||
|
<span class="identifier">optional</span><span class="special">&</span> <span class="keyword">operator</span> <span class="special">=</span> <span class="special">(</span> <span class="identifier">optional</span> <span class="keyword">const</span><span class="special">&</span> <span class="identifier">rhs</span> <span class="special">)</span> <span class="special">;</span> <a class="link" href="detailed_semantics.html#reference_optional_operator_equal_optional"><span class="inlinemediaobject"><img src="../../images/callouts/R.png" alt="R"></span></a>
|
||||||
|
|
||||||
|
<span class="identifier">optional</span><span class="special">&</span> <span class="keyword">operator</span> <span class="special">=</span> <span class="special">(</span> <span class="identifier">optional</span><span class="special">&&</span> <span class="identifier">rhs</span> <span class="special">)</span> <span class="keyword">noexcept</span><span class="special">(</span><span class="emphasis"><em>see below</em></span><span class="special">)</span> <span class="special">;</span> <a class="link" href="detailed_semantics.html#reference_optional_operator_move_equal_optional"><span class="inlinemediaobject"><img src="../../images/callouts/R.png" alt="R"></span></a>
|
||||||
|
|
||||||
|
<span class="keyword">template</span><span class="special"><</span><span class="keyword">class</span> <span class="identifier">U</span><span class="special">></span> <span class="identifier">optional</span><span class="special">&</span> <span class="keyword">operator</span> <span class="special">=</span> <span class="special">(</span> <span class="identifier">optional</span><span class="special"><</span><span class="identifier">U</span><span class="special">></span> <span class="keyword">const</span><span class="special">&</span> <span class="identifier">rhs</span> <span class="special">)</span> <span class="special">;</span> <a class="link" href="detailed_semantics.html#reference_optional_operator_equal_other_optional"><span class="inlinemediaobject"><img src="../../images/callouts/R.png" alt="R"></span></a>
|
||||||
|
|
||||||
|
<span class="keyword">template</span><span class="special"><</span><span class="keyword">class</span> <span class="identifier">U</span><span class="special">></span> <span class="identifier">optional</span><span class="special">&</span> <span class="keyword">operator</span> <span class="special">=</span> <span class="special">(</span> <span class="identifier">optional</span><span class="special"><</span><span class="identifier">U</span><span class="special">>&&</span> <span class="identifier">rhs</span> <span class="special">)</span> <span class="special">;</span> <a class="link" href="detailed_semantics.html#reference_optional_operator_move_equal_other_optional"><span class="inlinemediaobject"><img src="../../images/callouts/R.png" alt="R"></span></a>
|
||||||
|
|
||||||
|
<span class="keyword">template</span><span class="special"><</span><span class="keyword">class</span><span class="special">...</span> <span class="identifier">Args</span><span class="special">></span> <span class="keyword">void</span> <span class="identifier">emplace</span> <span class="special">(</span> <span class="identifier">Args</span><span class="special">...&&</span> <span class="identifier">args</span> <span class="special">)</span> <span class="special">;</span> <a class="link" href="detailed_semantics.html#reference_optional_emplace"><span class="inlinemediaobject"><img src="../../images/callouts/R.png" alt="R"></span></a>
|
||||||
|
|
||||||
|
<span class="keyword">template</span><span class="special"><</span><span class="keyword">class</span> <span class="identifier">InPlaceFactory</span><span class="special">></span> <span class="identifier">optional</span><span class="special">&</span> <span class="keyword">operator</span> <span class="special">=</span> <span class="special">(</span> <span class="identifier">InPlaceFactory</span> <span class="keyword">const</span><span class="special">&</span> <span class="identifier">f</span> <span class="special">)</span> <span class="special">;</span> <a class="link" href="detailed_semantics.html#reference_optional_operator_equal_factory"><span class="inlinemediaobject"><img src="../../images/callouts/R.png" alt="R"></span></a>
|
||||||
|
|
||||||
|
<span class="keyword">template</span><span class="special"><</span><span class="keyword">class</span> <span class="identifier">TypedInPlaceFactory</span><span class="special">></span> <span class="identifier">optional</span><span class="special">&</span> <span class="keyword">operator</span> <span class="special">=</span> <span class="special">(</span> <span class="identifier">TypedInPlaceFactory</span> <span class="keyword">const</span><span class="special">&</span> <span class="identifier">f</span> <span class="special">)</span> <span class="special">;</span> <a class="link" href="detailed_semantics.html#reference_optional_operator_equal_factory"><span class="inlinemediaobject"><img src="../../images/callouts/R.png" alt="R"></span></a>
|
||||||
|
|
||||||
|
<span class="identifier">T</span> <span class="keyword">const</span><span class="special">&</span> <span class="identifier">get</span><span class="special">()</span> <span class="keyword">const</span> <span class="special">;</span> <a class="link" href="detailed_semantics.html#reference_optional_get"><span class="inlinemediaobject"><img src="../../images/callouts/R.png" alt="R"></span></a>
|
||||||
|
<span class="identifier">T</span><span class="special">&</span> <span class="identifier">get</span><span class="special">()</span> <span class="special">;</span> <a class="link" href="detailed_semantics.html#reference_optional_get"><span class="inlinemediaobject"><img src="../../images/callouts/R.png" alt="R"></span></a>
|
||||||
|
|
||||||
|
<span class="identifier">T</span> <span class="keyword">const</span><span class="special">*</span> <span class="keyword">operator</span> <span class="special">->()</span> <span class="keyword">const</span> <span class="special">;</span> <a class="link" href="detailed_semantics.html#reference_optional_operator_arrow"><span class="inlinemediaobject"><img src="../../images/callouts/R.png" alt="R"></span></a>
|
||||||
|
<span class="identifier">T</span><span class="special">*</span> <span class="keyword">operator</span> <span class="special">->()</span> <span class="special">;</span> <a class="link" href="detailed_semantics.html#reference_optional_operator_arrow"><span class="inlinemediaobject"><img src="../../images/callouts/R.png" alt="R"></span></a>
|
||||||
|
|
||||||
|
<span class="identifier">T</span> <span class="keyword">const</span><span class="special">&</span> <span class="keyword">operator</span> <span class="special">*()</span> <span class="keyword">const</span><span class="special">&</span> <span class="special">;</span> <a class="link" href="detailed_semantics.html#reference_optional_operator_asterisk"><span class="inlinemediaobject"><img src="../../images/callouts/R.png" alt="R"></span></a>
|
||||||
|
<span class="identifier">T</span><span class="special">&</span> <span class="keyword">operator</span> <span class="special">*()</span> <span class="special">&;</span> <a class="link" href="detailed_semantics.html#reference_optional_operator_asterisk"><span class="inlinemediaobject"><img src="../../images/callouts/R.png" alt="R"></span></a>
|
||||||
|
<span class="identifier">T</span><span class="special">&&</span> <span class="keyword">operator</span> <span class="special">*()</span> <span class="special">&&;</span> <a class="link" href="detailed_semantics.html#reference_optional_operator_asterisk"><span class="inlinemediaobject"><img src="../../images/callouts/R.png" alt="R"></span></a>
|
||||||
|
|
||||||
|
<span class="identifier">T</span> <span class="keyword">const</span><span class="special">&</span> <span class="identifier">value</span><span class="special">()</span> <span class="keyword">const</span><span class="special">&</span> <span class="special">;</span> <a class="link" href="detailed_semantics.html#reference_optional_value"><span class="inlinemediaobject"><img src="../../images/callouts/R.png" alt="R"></span></a>
|
||||||
|
<span class="identifier">T</span><span class="special">&</span> <span class="identifier">value</span><span class="special">()</span> <span class="special">&</span> <span class="special">;</span> <a class="link" href="detailed_semantics.html#reference_optional_value"><span class="inlinemediaobject"><img src="../../images/callouts/R.png" alt="R"></span></a>
|
||||||
|
<span class="identifier">T</span><span class="special">&&</span> <span class="identifier">value</span><span class="special">()</span> <span class="special">&&</span> <span class="special">;</span> <a class="link" href="detailed_semantics.html#reference_optional_value"><span class="inlinemediaobject"><img src="../../images/callouts/R.png" alt="R"></span></a>
|
||||||
|
|
||||||
|
<span class="keyword">template</span><span class="special"><</span><span class="keyword">class</span> <span class="identifier">U</span><span class="special">></span> <span class="identifier">T</span> <span class="identifier">value_or</span><span class="special">(</span> <span class="identifier">U</span> <span class="special">&&</span> <span class="identifier">v</span> <span class="special">)</span> <span class="keyword">const</span><span class="special">&</span> <span class="special">;</span> <a class="link" href="detailed_semantics.html#reference_optional_value_or"><span class="inlinemediaobject"><img src="../../images/callouts/R.png" alt="R"></span></a>
|
||||||
|
<span class="keyword">template</span><span class="special"><</span><span class="keyword">class</span> <span class="identifier">U</span><span class="special">></span> <span class="identifier">T</span> <span class="identifier">value_or</span><span class="special">(</span> <span class="identifier">U</span> <span class="special">&&</span> <span class="identifier">v</span> <span class="special">)</span> <span class="special">&&</span> <span class="special">;</span> <a class="link" href="detailed_semantics.html#reference_optional_value_or"><span class="inlinemediaobject"><img src="../../images/callouts/R.png" alt="R"></span></a>
|
||||||
|
|
||||||
|
<span class="identifier">T</span> <span class="keyword">const</span><span class="special">*</span> <span class="identifier">get_ptr</span><span class="special">()</span> <span class="keyword">const</span> <span class="special">;</span> <a class="link" href="detailed_semantics.html#reference_optional_get_ptr"><span class="inlinemediaobject"><img src="../../images/callouts/R.png" alt="R"></span></a>
|
||||||
|
<span class="identifier">T</span><span class="special">*</span> <span class="identifier">get_ptr</span><span class="special">()</span> <span class="special">;</span> <a class="link" href="detailed_semantics.html#reference_optional_get_ptr"><span class="inlinemediaobject"><img src="../../images/callouts/R.png" alt="R"></span></a>
|
||||||
|
|
||||||
|
<span class="keyword">explicit</span> <span class="keyword">operator</span> <span class="keyword">bool</span><span class="special">()</span> <span class="keyword">const</span> <span class="special">;</span> <a class="link" href="detailed_semantics.html#reference_optional_operator_bool"><span class="inlinemediaobject"><img src="../../images/callouts/R.png" alt="R"></span></a>
|
||||||
|
|
||||||
|
<span class="keyword">bool</span> <span class="keyword">operator</span><span class="special">!()</span> <span class="keyword">const</span> <span class="keyword">noexcept</span> <span class="special">;</span> <a class="link" href="detailed_semantics.html#reference_optional_operator_not"><span class="inlinemediaobject"><img src="../../images/callouts/R.png" alt="R"></span></a>
|
||||||
|
|
||||||
|
<span class="comment">// deprecated methods</span>
|
||||||
|
|
||||||
|
<span class="comment">// (deprecated)</span>
|
||||||
|
<span class="keyword">void</span> <span class="identifier">reset</span><span class="special">()</span> <span class="keyword">noexcept</span> <span class="special">;</span> <a class="link" href="detailed_semantics.html#reference_optional_reset"><span class="inlinemediaobject"><img src="../../images/callouts/R.png" alt="R"></span></a>
|
||||||
|
|
||||||
|
<span class="comment">// (deprecated)</span>
|
||||||
|
<span class="keyword">void</span> <span class="identifier">reset</span> <span class="special">(</span> <span class="identifier">T</span> <span class="keyword">const</span><span class="special">&</span> <span class="special">)</span> <span class="special">;</span> <a class="link" href="detailed_semantics.html#reference_optional_reset_value"><span class="inlinemediaobject"><img src="../../images/callouts/R.png" alt="R"></span></a>
|
||||||
|
|
||||||
|
<span class="comment">// (deprecated)</span>
|
||||||
|
<span class="keyword">bool</span> <span class="identifier">is_initialized</span><span class="special">()</span> <span class="keyword">const</span> <span class="special">;</span> <a class="link" href="detailed_semantics.html#reference_optional_is_initialized"><span class="inlinemediaobject"><img src="../../images/callouts/R.png" alt="R"></span></a>
|
||||||
|
|
||||||
|
<span class="comment">// (deprecated)</span>
|
||||||
|
<span class="identifier">T</span> <span class="keyword">const</span><span class="special">&</span> <span class="identifier">get_value_or</span><span class="special">(</span> <span class="identifier">T</span> <span class="keyword">const</span><span class="special">&</span> <span class="keyword">default</span> <span class="special">)</span> <span class="keyword">const</span> <span class="special">;</span> <a class="link" href="detailed_semantics.html#reference_optional_get_value_or_value"><span class="inlinemediaobject"><img src="../../images/callouts/R.png" alt="R"></span></a>
|
||||||
|
<span class="special">};</span>
|
||||||
|
|
||||||
|
<span class="keyword">template</span><span class="special"><</span><span class="keyword">class</span> <span class="identifier">T</span><span class="special">></span> <span class="keyword">inline</span> <span class="keyword">bool</span> <span class="keyword">operator</span> <span class="special">==</span> <span class="special">(</span> <span class="identifier">optional</span><span class="special"><</span><span class="identifier">T</span><span class="special">></span> <span class="keyword">const</span><span class="special">&</span> <span class="identifier">x</span><span class="special">,</span> <span class="identifier">optional</span><span class="special"><</span><span class="identifier">T</span><span class="special">></span> <span class="keyword">const</span><span class="special">&</span> <span class="identifier">y</span> <span class="special">)</span> <span class="special">;</span> <a class="link" href="detailed_semantics.html#reference_operator_compare_equal_optional_optional"><span class="inlinemediaobject"><img src="../../images/callouts/R.png" alt="R"></span></a>
|
||||||
|
|
||||||
|
<span class="keyword">template</span><span class="special"><</span><span class="keyword">class</span> <span class="identifier">T</span><span class="special">></span> <span class="keyword">inline</span> <span class="keyword">bool</span> <span class="keyword">operator</span> <span class="special">!=</span> <span class="special">(</span> <span class="identifier">optional</span><span class="special"><</span><span class="identifier">T</span><span class="special">></span> <span class="keyword">const</span><span class="special">&</span> <span class="identifier">x</span><span class="special">,</span> <span class="identifier">optional</span><span class="special"><</span><span class="identifier">T</span><span class="special">></span> <span class="keyword">const</span><span class="special">&</span> <span class="identifier">y</span> <span class="special">)</span> <span class="special">;</span> <a class="link" href="detailed_semantics.html#reference_operator_compare_not_equal_optional_optional"><span class="inlinemediaobject"><img src="../../images/callouts/R.png" alt="R"></span></a>
|
||||||
|
|
||||||
|
<span class="keyword">template</span><span class="special"><</span><span class="keyword">class</span> <span class="identifier">T</span><span class="special">></span> <span class="keyword">inline</span> <span class="keyword">bool</span> <span class="keyword">operator</span> <span class="special"><</span> <span class="special">(</span> <span class="identifier">optional</span><span class="special"><</span><span class="identifier">T</span><span class="special">></span> <span class="keyword">const</span><span class="special">&</span> <span class="identifier">x</span><span class="special">,</span> <span class="identifier">optional</span><span class="special"><</span><span class="identifier">T</span><span class="special">></span> <span class="keyword">const</span><span class="special">&</span> <span class="identifier">y</span> <span class="special">)</span> <span class="special">;</span> <a class="link" href="detailed_semantics.html#reference_operator_compare_less_optional_optional"><span class="inlinemediaobject"><img src="../../images/callouts/R.png" alt="R"></span></a>
|
||||||
|
|
||||||
|
<span class="keyword">template</span><span class="special"><</span><span class="keyword">class</span> <span class="identifier">T</span><span class="special">></span> <span class="keyword">inline</span> <span class="keyword">bool</span> <span class="keyword">operator</span> <span class="special">></span> <span class="special">(</span> <span class="identifier">optional</span><span class="special"><</span><span class="identifier">T</span><span class="special">></span> <span class="keyword">const</span><span class="special">&</span> <span class="identifier">x</span><span class="special">,</span> <span class="identifier">optional</span><span class="special"><</span><span class="identifier">T</span><span class="special">></span> <span class="keyword">const</span><span class="special">&</span> <span class="identifier">y</span> <span class="special">)</span> <span class="special">;</span> <a class="link" href="detailed_semantics.html#reference_operator_compare_greater_optional_optional"><span class="inlinemediaobject"><img src="../../images/callouts/R.png" alt="R"></span></a>
|
||||||
|
|
||||||
|
<span class="keyword">template</span><span class="special"><</span><span class="keyword">class</span> <span class="identifier">T</span><span class="special">></span> <span class="keyword">inline</span> <span class="keyword">bool</span> <span class="keyword">operator</span> <span class="special"><=</span> <span class="special">(</span> <span class="identifier">optional</span><span class="special"><</span><span class="identifier">T</span><span class="special">></span> <span class="keyword">const</span><span class="special">&</span> <span class="identifier">x</span><span class="special">,</span> <span class="identifier">optional</span><span class="special"><</span><span class="identifier">T</span><span class="special">></span> <span class="keyword">const</span><span class="special">&</span> <span class="identifier">y</span> <span class="special">)</span> <span class="special">;</span> <a class="link" href="detailed_semantics.html#reference_operator_compare_less_or_equal_optional_optional"><span class="inlinemediaobject"><img src="../../images/callouts/R.png" alt="R"></span></a>
|
||||||
|
|
||||||
|
<span class="keyword">template</span><span class="special"><</span><span class="keyword">class</span> <span class="identifier">T</span><span class="special">></span> <span class="keyword">inline</span> <span class="keyword">bool</span> <span class="keyword">operator</span> <span class="special">>=</span> <span class="special">(</span> <span class="identifier">optional</span><span class="special"><</span><span class="identifier">T</span><span class="special">></span> <span class="keyword">const</span><span class="special">&</span> <span class="identifier">x</span><span class="special">,</span> <span class="identifier">optional</span><span class="special"><</span><span class="identifier">T</span><span class="special">></span> <span class="keyword">const</span><span class="special">&</span> <span class="identifier">y</span> <span class="special">)</span> <span class="special">;</span> <a class="link" href="detailed_semantics.html#reference_operator_compare_greater_or_equal_optional_optional"><span class="inlinemediaobject"><img src="../../images/callouts/R.png" alt="R"></span></a>
|
||||||
|
|
||||||
|
<span class="keyword">template</span><span class="special"><</span><span class="keyword">class</span> <span class="identifier">T</span><span class="special">></span> <span class="keyword">inline</span> <span class="keyword">bool</span> <span class="keyword">operator</span> <span class="special">==</span> <span class="special">(</span> <span class="identifier">optional</span><span class="special"><</span><span class="identifier">T</span><span class="special">></span> <span class="keyword">const</span><span class="special">&</span> <span class="identifier">x</span><span class="special">,</span> <span class="identifier">none_t</span> <span class="special">)</span> <span class="keyword">noexcept</span> <span class="special">;</span> <a class="link" href="detailed_semantics.html#reference_operator_compare_equal_optional_none"><span class="inlinemediaobject"><img src="../../images/callouts/R.png" alt="R"></span></a>
|
||||||
|
|
||||||
|
<span class="keyword">template</span><span class="special"><</span><span class="keyword">class</span> <span class="identifier">T</span><span class="special">></span> <span class="keyword">inline</span> <span class="keyword">bool</span> <span class="keyword">operator</span> <span class="special">!=</span> <span class="special">(</span> <span class="identifier">optional</span><span class="special"><</span><span class="identifier">T</span><span class="special">></span> <span class="keyword">const</span><span class="special">&</span> <span class="identifier">x</span><span class="special">,</span> <span class="identifier">none_t</span> <span class="special">)</span> <span class="keyword">noexcept</span> <span class="special">;</span> <a class="link" href="detailed_semantics.html#reference_operator_compare_not_equal_optional_none"><span class="inlinemediaobject"><img src="../../images/callouts/R.png" alt="R"></span></a>
|
||||||
|
|
||||||
|
<span class="keyword">template</span><span class="special"><</span><span class="keyword">class</span> <span class="identifier">T</span><span class="special">></span> <span class="keyword">inline</span> <span class="identifier">optional</span><span class="special"><</span><span class="identifier">T</span><span class="special">></span> <span class="identifier">make_optional</span> <span class="special">(</span> <span class="identifier">T</span> <span class="keyword">const</span><span class="special">&</span> <span class="identifier">v</span> <span class="special">)</span> <span class="special">;</span> <a class="link" href="detailed_semantics.html#reference_make_optional_value"><span class="inlinemediaobject"><img src="../../images/callouts/R.png" alt="R"></span></a>
|
||||||
|
|
||||||
|
<span class="keyword">template</span><span class="special"><</span><span class="keyword">class</span> <span class="identifier">T</span><span class="special">></span> <span class="keyword">inline</span> <span class="identifier">optional</span><span class="special"><</span><span class="identifier">T</span><span class="special">></span> <span class="identifier">make_optional</span> <span class="special">(</span> <span class="keyword">bool</span> <span class="identifier">condition</span><span class="special">,</span> <span class="identifier">T</span> <span class="keyword">const</span><span class="special">&</span> <span class="identifier">v</span> <span class="special">)</span> <span class="special">;</span> <a class="link" href="detailed_semantics.html#reference_make_optional_bool_value"><span class="inlinemediaobject"><img src="../../images/callouts/R.png" alt="R"></span></a>
|
||||||
|
|
||||||
|
<span class="keyword">template</span><span class="special"><</span><span class="keyword">class</span> <span class="identifier">T</span><span class="special">></span> <span class="keyword">inline</span> <span class="identifier">T</span> <span class="keyword">const</span><span class="special">&</span> <span class="identifier">get_optional_value_or</span> <span class="special">(</span> <span class="identifier">optional</span><span class="special"><</span><span class="identifier">T</span><span class="special">></span> <span class="keyword">const</span><span class="special">&</span> <span class="identifier">opt</span><span class="special">,</span> <span class="identifier">T</span> <span class="keyword">const</span><span class="special">&</span> <span class="keyword">default</span> <span class="special">)</span> <span class="special">;</span> <a class="link" href="detailed_semantics.html#reference_optional_get_value_or_value"><span class="inlinemediaobject"><img src="../../images/callouts/R.png" alt="R"></span></a>
|
||||||
|
|
||||||
|
<span class="keyword">template</span><span class="special"><</span><span class="keyword">class</span> <span class="identifier">T</span><span class="special">></span> <span class="keyword">inline</span> <span class="identifier">T</span> <span class="keyword">const</span><span class="special">&</span> <span class="identifier">get</span> <span class="special">(</span> <span class="identifier">optional</span><span class="special"><</span><span class="identifier">T</span><span class="special">></span> <span class="keyword">const</span><span class="special">&</span> <span class="identifier">opt</span> <span class="special">)</span> <span class="special">;</span> <a class="link" href="detailed_semantics.html#reference_optional_get"><span class="inlinemediaobject"><img src="../../images/callouts/R.png" alt="R"></span></a>
|
||||||
|
|
||||||
|
<span class="keyword">template</span><span class="special"><</span><span class="keyword">class</span> <span class="identifier">T</span><span class="special">></span> <span class="keyword">inline</span> <span class="identifier">T</span><span class="special">&</span> <span class="identifier">get</span> <span class="special">(</span> <span class="identifier">optional</span><span class="special"><</span><span class="identifier">T</span><span class="special">></span> <span class="special">&</span> <span class="identifier">opt</span> <span class="special">)</span> <span class="special">;</span> <a class="link" href="detailed_semantics.html#reference_optional_get"><span class="inlinemediaobject"><img src="../../images/callouts/R.png" alt="R"></span></a>
|
||||||
|
|
||||||
|
<span class="keyword">template</span><span class="special"><</span><span class="keyword">class</span> <span class="identifier">T</span><span class="special">></span> <span class="keyword">inline</span> <span class="identifier">T</span> <span class="keyword">const</span><span class="special">*</span> <span class="identifier">get</span> <span class="special">(</span> <span class="identifier">optional</span><span class="special"><</span><span class="identifier">T</span><span class="special">></span> <span class="keyword">const</span><span class="special">*</span> <span class="identifier">opt</span> <span class="special">)</span> <span class="special">;</span> <a class="link" href="detailed_semantics.html#reference_optional_get"><span class="inlinemediaobject"><img src="../../images/callouts/R.png" alt="R"></span></a>
|
||||||
|
|
||||||
|
<span class="keyword">template</span><span class="special"><</span><span class="keyword">class</span> <span class="identifier">T</span><span class="special">></span> <span class="keyword">inline</span> <span class="identifier">T</span><span class="special">*</span> <span class="identifier">get</span> <span class="special">(</span> <span class="identifier">optional</span><span class="special"><</span><span class="identifier">T</span><span class="special">>*</span> <span class="identifier">opt</span> <span class="special">)</span> <span class="special">;</span> <a class="link" href="detailed_semantics.html#reference_optional_get"><span class="inlinemediaobject"><img src="../../images/callouts/R.png" alt="R"></span></a>
|
||||||
|
|
||||||
|
<span class="keyword">template</span><span class="special"><</span><span class="keyword">class</span> <span class="identifier">T</span><span class="special">></span> <span class="keyword">inline</span> <span class="identifier">T</span> <span class="keyword">const</span><span class="special">*</span> <span class="identifier">get_pointer</span> <span class="special">(</span> <span class="identifier">optional</span><span class="special"><</span><span class="identifier">T</span><span class="special">></span> <span class="keyword">const</span><span class="special">&</span> <span class="identifier">opt</span> <span class="special">)</span> <span class="special">;</span> <a class="link" href="detailed_semantics.html#reference_optional_get_ptr"><span class="inlinemediaobject"><img src="../../images/callouts/R.png" alt="R"></span></a>
|
||||||
|
|
||||||
|
<span class="keyword">template</span><span class="special"><</span><span class="keyword">class</span> <span class="identifier">T</span><span class="special">></span> <span class="keyword">inline</span> <span class="identifier">T</span><span class="special">*</span> <span class="identifier">get_pointer</span> <span class="special">(</span> <span class="identifier">optional</span><span class="special"><</span><span class="identifier">T</span><span class="special">></span> <span class="special">&</span> <span class="identifier">opt</span> <span class="special">)</span> <span class="special">;</span> <a class="link" href="detailed_semantics.html#reference_optional_get_ptr"><span class="inlinemediaobject"><img src="../../images/callouts/R.png" alt="R"></span></a>
|
||||||
|
|
||||||
|
<span class="keyword">template</span><span class="special"><</span><span class="keyword">class</span> <span class="identifier">T</span><span class="special">></span> <span class="keyword">inline</span> <span class="keyword">void</span> <span class="identifier">swap</span><span class="special">(</span> <span class="identifier">optional</span><span class="special"><</span><span class="identifier">T</span><span class="special">>&</span> <span class="identifier">x</span><span class="special">,</span> <span class="identifier">optional</span><span class="special"><</span><span class="identifier">T</span><span class="special">>&</span> <span class="identifier">y</span> <span class="special">)</span> <span class="special">;</span> <a class="link" href="detailed_semantics.html#reference_swap_optional_optional"><span class="inlinemediaobject"><img src="../../images/callouts/R.png" alt="R"></span></a>
|
||||||
|
|
||||||
|
<span class="special">}</span> <span class="comment">// namespace boost</span>
|
||||||
|
</pre>
|
||||||
|
</div>
|
||||||
|
<table xmlns:rev="http://www.cs.rpi.edu/~gregod/boost/tools/doc/revision" width="100%"><tr>
|
||||||
|
<td align="left"></td>
|
||||||
|
<td align="right"><div class="copyright-footer">Copyright © 2003-2007 Fernando Luis Cacciola Carballal<br>Copyright © 2014 Andrzej Krzemieński<p>
|
||||||
|
Distributed under the Boost Software License, Version 1.0. (See accompanying
|
||||||
|
file LICENSE_1_0.txt or copy at <a href="http://www.boost.org/LICENSE_1_0.txt" target="_top">http://www.boost.org/LICENSE_1_0.txt</a>)
|
||||||
|
</p>
|
||||||
|
</div></td>
|
||||||
|
</tr></table>
|
||||||
|
<hr>
|
||||||
|
<div class="spirit-nav">
|
||||||
|
<a accesskey="p" href="../../optional/reference.html"><img src="../../../../../../doc/src/images/prev.png" alt="Prev"></a><a accesskey="u" href="../../optional/reference.html"><img src="../../../../../../doc/src/images/up.png" alt="Up"></a><a accesskey="h" href="../../index.html"><img src="../../../../../../doc/src/images/home.png" alt="Home"></a><a accesskey="n" href="detailed_semantics.html"><img src="../../../../../../doc/src/images/next.png" alt="Next"></a>
|
||||||
|
</div>
|
||||||
|
</body>
|
||||||
|
</html>
|
@ -6,7 +6,7 @@
|
|||||||
<meta name="generator" content="DocBook XSL Stylesheets V1.78.1">
|
<meta name="generator" content="DocBook XSL Stylesheets V1.78.1">
|
||||||
<link rel="home" href="../index.html" title="Chapter 1. Boost.Optional">
|
<link rel="home" href="../index.html" title="Chapter 1. Boost.Optional">
|
||||||
<link rel="up" href="../index.html" title="Chapter 1. Boost.Optional">
|
<link rel="up" href="../index.html" title="Chapter 1. Boost.Optional">
|
||||||
<link rel="prev" href="development.html" title="Development">
|
<link rel="prev" href="tutorial/type_requirements.html" title="Type requirements">
|
||||||
<link rel="next" href="detailed_semantics.html" title="Detailed Semantics">
|
<link rel="next" href="detailed_semantics.html" title="Detailed Semantics">
|
||||||
</head>
|
</head>
|
||||||
<body bgcolor="white" text="black" link="#0000FF" vlink="#840084" alink="#0000FF">
|
<body bgcolor="white" text="black" link="#0000FF" vlink="#840084" alink="#0000FF">
|
||||||
@ -20,7 +20,7 @@
|
|||||||
</tr></table>
|
</tr></table>
|
||||||
<hr>
|
<hr>
|
||||||
<div class="spirit-nav">
|
<div class="spirit-nav">
|
||||||
<a accesskey="p" href="development.html"><img src="../../../../../doc/src/images/prev.png" alt="Prev"></a><a accesskey="u" href="../index.html"><img src="../../../../../doc/src/images/up.png" alt="Up"></a><a accesskey="h" href="../index.html"><img src="../../../../../doc/src/images/home.png" alt="Home"></a><a accesskey="n" href="detailed_semantics.html"><img src="../../../../../doc/src/images/next.png" alt="Next"></a>
|
<a accesskey="p" href="tutorial/type_requirements.html"><img src="../../../../../doc/src/images/prev.png" alt="Prev"></a><a accesskey="u" href="../index.html"><img src="../../../../../doc/src/images/up.png" alt="Up"></a><a accesskey="h" href="../index.html"><img src="../../../../../doc/src/images/home.png" alt="Home"></a><a accesskey="n" href="detailed_semantics.html"><img src="../../../../../doc/src/images/next.png" alt="Next"></a>
|
||||||
</div>
|
</div>
|
||||||
<div class="section">
|
<div class="section">
|
||||||
<div class="titlepage"><div><div><h2 class="title" style="clear: both">
|
<div class="titlepage"><div><div><h2 class="title" style="clear: both">
|
||||||
@ -86,13 +86,16 @@
|
|||||||
<span class="identifier">T</span> <span class="keyword">const</span><span class="special">*</span> <span class="keyword">operator</span> <span class="special">->()</span> <span class="keyword">const</span> <span class="special">;</span> <a class="link" href="detailed_semantics.html#reference_optional_operator_arrow"><span class="inlinemediaobject"><img src="../images/callouts/R.png" alt="R"></span></a>
|
<span class="identifier">T</span> <span class="keyword">const</span><span class="special">*</span> <span class="keyword">operator</span> <span class="special">->()</span> <span class="keyword">const</span> <span class="special">;</span> <a class="link" href="detailed_semantics.html#reference_optional_operator_arrow"><span class="inlinemediaobject"><img src="../images/callouts/R.png" alt="R"></span></a>
|
||||||
<span class="identifier">T</span><span class="special">*</span> <span class="keyword">operator</span> <span class="special">->()</span> <span class="special">;</span> <a class="link" href="detailed_semantics.html#reference_optional_operator_arrow"><span class="inlinemediaobject"><img src="../images/callouts/R.png" alt="R"></span></a>
|
<span class="identifier">T</span><span class="special">*</span> <span class="keyword">operator</span> <span class="special">->()</span> <span class="special">;</span> <a class="link" href="detailed_semantics.html#reference_optional_operator_arrow"><span class="inlinemediaobject"><img src="../images/callouts/R.png" alt="R"></span></a>
|
||||||
|
|
||||||
<span class="identifier">T</span> <span class="keyword">const</span><span class="special">&</span> <span class="keyword">operator</span> <span class="special">*()</span> <span class="keyword">const</span> <span class="special">;</span> <a class="link" href="detailed_semantics.html#reference_optional_get"><span class="inlinemediaobject"><img src="../images/callouts/R.png" alt="R"></span></a>
|
<span class="identifier">T</span> <span class="keyword">const</span><span class="special">&</span> <span class="keyword">operator</span> <span class="special">*()</span> <span class="keyword">const</span><span class="special">&</span> <span class="special">;</span> <a class="link" href="detailed_semantics.html#reference_optional_operator_asterisk"><span class="inlinemediaobject"><img src="../images/callouts/R.png" alt="R"></span></a>
|
||||||
<span class="identifier">T</span><span class="special">&</span> <span class="keyword">operator</span> <span class="special">*()</span> <span class="special">;</span> <a class="link" href="detailed_semantics.html#reference_optional_get"><span class="inlinemediaobject"><img src="../images/callouts/R.png" alt="R"></span></a>
|
<span class="identifier">T</span><span class="special">&</span> <span class="keyword">operator</span> <span class="special">*()</span> <span class="special">&;</span> <a class="link" href="detailed_semantics.html#reference_optional_operator_asterisk"><span class="inlinemediaobject"><img src="../images/callouts/R.png" alt="R"></span></a>
|
||||||
|
<span class="identifier">T</span><span class="special">&&</span> <span class="keyword">operator</span> <span class="special">*()</span> <span class="special">&&;</span> <a class="link" href="detailed_semantics.html#reference_optional_operator_asterisk"><span class="inlinemediaobject"><img src="../images/callouts/R.png" alt="R"></span></a>
|
||||||
|
|
||||||
<span class="identifier">T</span> <span class="keyword">const</span><span class="special">&</span> <span class="identifier">value</span><span class="special">()</span> <span class="keyword">const</span> <span class="special">;</span> <a class="link" href="detailed_semantics.html#reference_optional_value"><span class="inlinemediaobject"><img src="../images/callouts/R.png" alt="R"></span></a>
|
<span class="identifier">T</span> <span class="keyword">const</span><span class="special">&</span> <span class="identifier">value</span><span class="special">()</span> <span class="keyword">const</span><span class="special">&</span> <span class="special">;</span> <a class="link" href="detailed_semantics.html#reference_optional_value"><span class="inlinemediaobject"><img src="../images/callouts/R.png" alt="R"></span></a>
|
||||||
<span class="identifier">T</span><span class="special">&</span> <span class="identifier">value</span><span class="special">()</span> <span class="special">;</span> <a class="link" href="detailed_semantics.html#reference_optional_value"><span class="inlinemediaobject"><img src="../images/callouts/R.png" alt="R"></span></a>
|
<span class="identifier">T</span><span class="special">&</span> <span class="identifier">value</span><span class="special">()</span> <span class="special">&</span> <span class="special">;</span> <a class="link" href="detailed_semantics.html#reference_optional_value"><span class="inlinemediaobject"><img src="../images/callouts/R.png" alt="R"></span></a>
|
||||||
|
<span class="identifier">T</span><span class="special">&&</span> <span class="identifier">value</span><span class="special">()</span> <span class="special">&&</span> <span class="special">;</span> <a class="link" href="detailed_semantics.html#reference_optional_value"><span class="inlinemediaobject"><img src="../images/callouts/R.png" alt="R"></span></a>
|
||||||
|
|
||||||
<span class="keyword">template</span><span class="special"><</span><span class="keyword">class</span> <span class="identifier">U</span><span class="special">></span> <span class="identifier">T</span> <span class="identifier">value_or</span><span class="special">(</span> <span class="identifier">U</span> <span class="special">&&</span> <span class="identifier">v</span> <span class="special">)</span> <span class="keyword">const</span> <span class="special">;</span> <a class="link" href="detailed_semantics.html#reference_optional_value_or"><span class="inlinemediaobject"><img src="../images/callouts/R.png" alt="R"></span></a>
|
<span class="keyword">template</span><span class="special"><</span><span class="keyword">class</span> <span class="identifier">U</span><span class="special">></span> <span class="identifier">T</span> <span class="identifier">value_or</span><span class="special">(</span> <span class="identifier">U</span> <span class="special">&&</span> <span class="identifier">v</span> <span class="special">)</span> <span class="keyword">const</span><span class="special">&</span> <span class="special">;</span> <a class="link" href="detailed_semantics.html#reference_optional_value_or"><span class="inlinemediaobject"><img src="../images/callouts/R.png" alt="R"></span></a>
|
||||||
|
<span class="keyword">template</span><span class="special"><</span><span class="keyword">class</span> <span class="identifier">U</span><span class="special">></span> <span class="identifier">T</span> <span class="identifier">value_or</span><span class="special">(</span> <span class="identifier">U</span> <span class="special">&&</span> <span class="identifier">v</span> <span class="special">)</span> <span class="special">&&</span> <span class="special">;</span> <a class="link" href="detailed_semantics.html#reference_optional_value_or"><span class="inlinemediaobject"><img src="../images/callouts/R.png" alt="R"></span></a>
|
||||||
|
|
||||||
<span class="identifier">T</span> <span class="keyword">const</span><span class="special">*</span> <span class="identifier">get_ptr</span><span class="special">()</span> <span class="keyword">const</span> <span class="special">;</span> <a class="link" href="detailed_semantics.html#reference_optional_get_ptr"><span class="inlinemediaobject"><img src="../images/callouts/R.png" alt="R"></span></a>
|
<span class="identifier">T</span> <span class="keyword">const</span><span class="special">*</span> <span class="identifier">get_ptr</span><span class="special">()</span> <span class="keyword">const</span> <span class="special">;</span> <a class="link" href="detailed_semantics.html#reference_optional_get_ptr"><span class="inlinemediaobject"><img src="../images/callouts/R.png" alt="R"></span></a>
|
||||||
<span class="identifier">T</span><span class="special">*</span> <span class="identifier">get_ptr</span><span class="special">()</span> <span class="special">;</span> <a class="link" href="detailed_semantics.html#reference_optional_get_ptr"><span class="inlinemediaobject"><img src="../images/callouts/R.png" alt="R"></span></a>
|
<span class="identifier">T</span><span class="special">*</span> <span class="identifier">get_ptr</span><span class="special">()</span> <span class="special">;</span> <a class="link" href="detailed_semantics.html#reference_optional_get_ptr"><span class="inlinemediaobject"><img src="../images/callouts/R.png" alt="R"></span></a>
|
||||||
@ -165,7 +168,7 @@
|
|||||||
</tr></table>
|
</tr></table>
|
||||||
<hr>
|
<hr>
|
||||||
<div class="spirit-nav">
|
<div class="spirit-nav">
|
||||||
<a accesskey="p" href="development.html"><img src="../../../../../doc/src/images/prev.png" alt="Prev"></a><a accesskey="u" href="../index.html"><img src="../../../../../doc/src/images/up.png" alt="Up"></a><a accesskey="h" href="../index.html"><img src="../../../../../doc/src/images/home.png" alt="Home"></a><a accesskey="n" href="detailed_semantics.html"><img src="../../../../../doc/src/images/next.png" alt="Next"></a>
|
<a accesskey="p" href="tutorial/type_requirements.html"><img src="../../../../../doc/src/images/prev.png" alt="Prev"></a><a accesskey="u" href="../index.html"><img src="../../../../../doc/src/images/up.png" alt="Up"></a><a accesskey="h" href="../index.html"><img src="../../../../../doc/src/images/home.png" alt="Home"></a><a accesskey="n" href="detailed_semantics.html"><img src="../../../../../doc/src/images/next.png" alt="Next"></a>
|
||||||
</div>
|
</div>
|
||||||
</body>
|
</body>
|
||||||
</html>
|
</html>
|
||||||
|
@ -6,8 +6,8 @@
|
|||||||
<meta name="generator" content="DocBook XSL Stylesheets V1.78.1">
|
<meta name="generator" content="DocBook XSL Stylesheets V1.78.1">
|
||||||
<link rel="home" href="../index.html" title="Chapter 1. Boost.Optional">
|
<link rel="home" href="../index.html" title="Chapter 1. Boost.Optional">
|
||||||
<link rel="up" href="../index.html" title="Chapter 1. Boost.Optional">
|
<link rel="up" href="../index.html" title="Chapter 1. Boost.Optional">
|
||||||
<link rel="prev" href="../index.html" title="Chapter 1. Boost.Optional">
|
<link rel="prev" href="quick_start.html" title="Quick Start">
|
||||||
<link rel="next" href="discussion.html" title="Discussion">
|
<link rel="next" href="synopsis.html" title="Synopsis">
|
||||||
</head>
|
</head>
|
||||||
<body bgcolor="white" text="black" link="#0000FF" vlink="#840084" alink="#0000FF">
|
<body bgcolor="white" text="black" link="#0000FF" vlink="#840084" alink="#0000FF">
|
||||||
<table cellpadding="2" width="100%"><tr>
|
<table cellpadding="2" width="100%"><tr>
|
||||||
@ -20,207 +20,491 @@
|
|||||||
</tr></table>
|
</tr></table>
|
||||||
<hr>
|
<hr>
|
||||||
<div class="spirit-nav">
|
<div class="spirit-nav">
|
||||||
<a accesskey="p" href="../index.html"><img src="../../../../../doc/src/images/prev.png" alt="Prev"></a><a accesskey="u" href="../index.html"><img src="../../../../../doc/src/images/up.png" alt="Up"></a><a accesskey="h" href="../index.html"><img src="../../../../../doc/src/images/home.png" alt="Home"></a><a accesskey="n" href="discussion.html"><img src="../../../../../doc/src/images/next.png" alt="Next"></a>
|
<a accesskey="p" href="quick_start.html"><img src="../../../../../doc/src/images/prev.png" alt="Prev"></a><a accesskey="u" href="../index.html"><img src="../../../../../doc/src/images/up.png" alt="Up"></a><a accesskey="h" href="../index.html"><img src="../../../../../doc/src/images/home.png" alt="Home"></a><a accesskey="n" href="synopsis.html"><img src="../../../../../doc/src/images/next.png" alt="Next"></a>
|
||||||
</div>
|
</div>
|
||||||
<div class="section">
|
<div class="section">
|
||||||
<div class="titlepage"><div><div><h2 class="title" style="clear: both">
|
<div class="titlepage"><div><div><h2 class="title" style="clear: both">
|
||||||
<a name="boost_optional.tutorial"></a><a class="link" href="tutorial.html" title="Tutorial">Tutorial</a>
|
<a name="boost_optional.tutorial"></a><a class="link" href="tutorial.html" title="Tutorial">Tutorial</a>
|
||||||
</h2></div></div></div>
|
</h2></div></div></div>
|
||||||
<div class="toc"><dl class="toc">
|
<div class="toc"><dl class="toc">
|
||||||
<dt><span class="section"><a href="tutorial.html#boost_optional.tutorial.optional_return_values">Optional
|
<dt><span class="section"><a href="tutorial.html#boost_optional.tutorial.motivation">Motivation</a></span></dt>
|
||||||
return values</a></span></dt>
|
<dt><span class="section"><a href="tutorial.html#boost_optional.tutorial.design_overview">Design Overview</a></span></dt>
|
||||||
<dt><span class="section"><a href="tutorial.html#boost_optional.tutorial.optional_data_members">Optional
|
|
||||||
data members</a></span></dt>
|
|
||||||
<dt><span class="section"><a href="tutorial.html#boost_optional.tutorial.bypassing_unnecessary_default_construction">Bypassing
|
|
||||||
unnecessary default construction</a></span></dt>
|
|
||||||
</dl></div>
|
</dl></div>
|
||||||
<div class="section">
|
<div class="section">
|
||||||
<div class="titlepage"><div><div><h3 class="title">
|
<div class="titlepage"><div><div><h3 class="title">
|
||||||
<a name="boost_optional.tutorial.optional_return_values"></a><a class="link" href="tutorial.html#boost_optional.tutorial.optional_return_values" title="Optional return values">Optional
|
<a name="boost_optional.tutorial.motivation"></a><a class="link" href="tutorial.html#boost_optional.tutorial.motivation" title="Motivation">Motivation</a>
|
||||||
return values</a>
|
|
||||||
</h3></div></div></div>
|
</h3></div></div></div>
|
||||||
<p>
|
<p>
|
||||||
Let's write and use a converter function that converts an a <code class="computeroutput"><span class="identifier">std</span><span class="special">::</span><span class="identifier">string</span></code>
|
Consider these functions which should return a value but which might not
|
||||||
to an <code class="computeroutput"><span class="keyword">int</span></code>. It is possible that
|
have a value to return:
|
||||||
for a given string (e.g. <code class="computeroutput"><span class="string">"cat"</span></code>)
|
|
||||||
there exist no value of type <code class="computeroutput"><span class="keyword">int</span></code>
|
|
||||||
capable of representing the conversion result. We do not consider such situation
|
|
||||||
an error. We expect that the converter can be used only to check if the conversion
|
|
||||||
is possible. A natural signature for this function can be:
|
|
||||||
</p>
|
</p>
|
||||||
<pre class="programlisting"><span class="preprocessor">#include</span> <span class="special"><</span><span class="identifier">boost</span><span class="special">/</span><span class="identifier">optional</span><span class="special">.</span><span class="identifier">hpp</span><span class="special">></span>
|
<div class="itemizedlist"><ul class="itemizedlist" style="list-style-type: disc; ">
|
||||||
<span class="identifier">boost</span><span class="special">::</span><span class="identifier">optionl</span><span class="special"><</span><span class="keyword">int</span><span class="special">></span> <span class="identifier">convert</span><span class="special">(</span><span class="keyword">const</span> <span class="identifier">std</span><span class="special">::</span><span class="identifier">string</span><span class="special">&</span> <span class="identifier">text</span><span class="special">);</span>
|
<li class="listitem">
|
||||||
|
(A) <code class="computeroutput"><span class="keyword">double</span> <span class="identifier">sqrt</span><span class="special">(</span><span class="keyword">double</span> <span class="identifier">n</span> <span class="special">);</span></code>
|
||||||
|
</li>
|
||||||
|
<li class="listitem">
|
||||||
|
(B) <code class="computeroutput"><span class="keyword">char</span> <span class="identifier">get_async_input</span><span class="special">();</span></code>
|
||||||
|
</li>
|
||||||
|
<li class="listitem">
|
||||||
|
(C) <code class="computeroutput"><span class="identifier">point</span> <span class="identifier">polygon</span><span class="special">::</span><span class="identifier">get_any_point_effectively_inside</span><span class="special">();</span></code>
|
||||||
|
</li>
|
||||||
|
</ul></div>
|
||||||
|
<p>
|
||||||
|
There are different approaches to the issue of not having a value to return.
|
||||||
|
</p>
|
||||||
|
<p>
|
||||||
|
A typical approach is to consider the existence of a valid return value as
|
||||||
|
a postcondition, so that if the function cannot compute the value to return,
|
||||||
|
it has either undefined behavior (and can use assert in a debug build) or
|
||||||
|
uses a runtime check and throws an exception if the postcondition is violated.
|
||||||
|
This is a reasonable choice for example, for function (A), because the lack
|
||||||
|
of a proper return value is directly related to an invalid parameter (out
|
||||||
|
of domain argument), so it is appropriate to require the callee to supply
|
||||||
|
only parameters in a valid domain for execution to continue normally.
|
||||||
|
</p>
|
||||||
|
<p>
|
||||||
|
However, function (B), because of its asynchronous nature, does not fail
|
||||||
|
just because it can't find a value to return; so it is incorrect to consider
|
||||||
|
such a situation an error and assert or throw an exception. This function
|
||||||
|
must return, and somehow, must tell the callee that it is not returning a
|
||||||
|
meaningful value.
|
||||||
|
</p>
|
||||||
|
<p>
|
||||||
|
A similar situation occurs with function (C): it is conceptually an error
|
||||||
|
to ask a <span class="emphasis"><em>null-area</em></span> polygon to return a point inside
|
||||||
|
itself, but in many applications, it is just impractical for performance
|
||||||
|
reasons to treat this as an error (because detecting that the polygon has
|
||||||
|
no area might be too expensive to be required to be tested previously), and
|
||||||
|
either an arbitrary point (typically at infinity) is returned, or some efficient
|
||||||
|
way to tell the callee that there is no such point is used.
|
||||||
|
</p>
|
||||||
|
<p>
|
||||||
|
There are various mechanisms to let functions communicate that the returned
|
||||||
|
value is not valid. One such mechanism, which is quite common since it has
|
||||||
|
zero or negligible overhead, is to use a special value which is reserved
|
||||||
|
to communicate this. Classical examples of such special values are <code class="computeroutput"><span class="identifier">EOF</span></code>, <code class="computeroutput"><span class="identifier">string</span><span class="special">::</span><span class="identifier">npos</span></code>,
|
||||||
|
points at infinity, etc...
|
||||||
|
</p>
|
||||||
|
<p>
|
||||||
|
When those values exist, i.e. the return type can hold all meaningful values
|
||||||
|
<span class="emphasis"><em>plus</em></span> the <span class="emphasis"><em>signal</em></span> value, this mechanism
|
||||||
|
is quite appropriate and well known. Unfortunately, there are cases when
|
||||||
|
such values do not exist. In these cases, the usual alternative is either
|
||||||
|
to use a wider type, such as <code class="computeroutput"><span class="keyword">int</span></code>
|
||||||
|
in place of <code class="computeroutput"><span class="keyword">char</span></code>; or a compound
|
||||||
|
type, such as <code class="computeroutput"><span class="identifier">std</span><span class="special">::</span><span class="identifier">pair</span><span class="special"><</span><span class="identifier">point</span><span class="special">,</span><span class="keyword">bool</span><span class="special">></span></code>.
|
||||||
|
</p>
|
||||||
|
<p>
|
||||||
|
Returning a <code class="computeroutput"><span class="identifier">std</span><span class="special">::</span><span class="identifier">pair</span><span class="special"><</span><span class="identifier">T</span><span class="special">,</span><span class="keyword">bool</span><span class="special">></span></code>, thus attaching a boolean flag to the
|
||||||
|
result which indicates if the result is meaningful, has the advantage that
|
||||||
|
can be turned into a consistent idiom since the first element of the pair
|
||||||
|
can be whatever the function would conceptually return. For example, the
|
||||||
|
last two functions could have the following interface:
|
||||||
|
</p>
|
||||||
|
<pre class="programlisting"><span class="identifier">std</span><span class="special">::</span><span class="identifier">pair</span><span class="special"><</span><span class="keyword">char</span><span class="special">,</span><span class="keyword">bool</span><span class="special">></span> <span class="identifier">get_async_input</span><span class="special">();</span>
|
||||||
|
<span class="identifier">std</span><span class="special">::</span><span class="identifier">pair</span><span class="special"><</span><span class="identifier">point</span><span class="special">,</span><span class="keyword">bool</span><span class="special">></span> <span class="identifier">polygon</span><span class="special">::</span><span class="identifier">get_any_point_effectively_inside</span><span class="special">();</span>
|
||||||
</pre>
|
</pre>
|
||||||
<p>
|
<p>
|
||||||
All necessary functionality can be included with one header <code class="computeroutput"><span class="special"><</span><span class="identifier">boost</span><span class="special">/</span><span class="identifier">optional</span><span class="special">.</span><span class="identifier">hpp</span><span class="special">></span></code>.
|
These functions use a consistent interface for dealing with possibly nonexistent
|
||||||
The above function signature means that the function can either return a
|
results:
|
||||||
value of type <code class="computeroutput"><span class="keyword">int</span></code> or a flag
|
|
||||||
indicating that no value of <code class="computeroutput"><span class="keyword">int</span></code>
|
|
||||||
is available. This does not indicate an error. It is like one additional
|
|
||||||
value of <code class="computeroutput"><span class="keyword">int</span></code>. This is how we
|
|
||||||
can use our function:
|
|
||||||
</p>
|
</p>
|
||||||
<pre class="programlisting"><span class="keyword">const</span> <span class="identifier">std</span><span class="special">::</span><span class="identifier">string</span><span class="special">&</span> <span class="identifier">text</span> <span class="special">=</span> <span class="comment">/*... */</span><span class="special">;</span>
|
<pre class="programlisting"><span class="identifier">std</span><span class="special">::</span><span class="identifier">pair</span><span class="special"><</span><span class="identifier">point</span><span class="special">,</span><span class="keyword">bool</span><span class="special">></span> <span class="identifier">p</span> <span class="special">=</span> <span class="identifier">poly</span><span class="special">.</span><span class="identifier">get_any_point_effectively_inside</span><span class="special">();</span>
|
||||||
<span class="identifier">boost</span><span class="special">::</span><span class="identifier">optionl</span><span class="special"><</span><span class="keyword">int</span><span class="special">></span> <span class="identifier">oi</span> <span class="special">=</span> <span class="identifier">convert</span><span class="special">(</span><span class="identifier">text</span><span class="special">);</span> <span class="comment">// move-construct</span>
|
<span class="keyword">if</span> <span class="special">(</span> <span class="identifier">p</span><span class="special">.</span><span class="identifier">second</span> <span class="special">)</span>
|
||||||
<span class="keyword">if</span> <span class="special">(</span><span class="identifier">oi</span><span class="special">)</span> <span class="comment">// contextual conversion to bool</span>
|
<span class="identifier">flood_fill</span><span class="special">(</span><span class="identifier">p</span><span class="special">.</span><span class="identifier">first</span><span class="special">);</span>
|
||||||
<span class="keyword">int</span> <span class="identifier">i</span> <span class="special">=</span> <span class="special">*</span><span class="identifier">oi</span><span class="special">;</span> <span class="comment">// operator*</span>
|
|
||||||
</pre>
|
</pre>
|
||||||
<p>
|
<p>
|
||||||
In order to test if <code class="computeroutput"><span class="identifier">optional</span></code>
|
However, not only is this quite a burden syntactically, it is also error
|
||||||
contains a value, we use the contextual conversion to type <code class="computeroutput"><span class="keyword">bool</span></code>. Because of this we can combine the initialization
|
prone since the user can easily use the function result (first element of
|
||||||
of the optional object and the test into one instruction:
|
the pair) without ever checking if it has a valid value.
|
||||||
</p>
|
</p>
|
||||||
<pre class="programlisting"><span class="keyword">if</span> <span class="special">(</span><span class="identifier">boost</span><span class="special">::</span><span class="identifier">optionl</span><span class="special"><</span><span class="keyword">int</span><span class="special">></span> <span class="identifier">oi</span> <span class="special">=</span> <span class="identifier">convert</span><span class="special">(</span><span class="identifier">text</span><span class="special">))</span>
|
|
||||||
<span class="keyword">int</span> <span class="identifier">i</span> <span class="special">=</span> <span class="special">*</span><span class="identifier">oi</span><span class="special">;</span>
|
|
||||||
</pre>
|
|
||||||
<p>
|
<p>
|
||||||
We extract the contained value with <code class="computeroutput"><span class="keyword">operator</span><span class="special">*</span></code> (and with <code class="computeroutput"><span class="keyword">operator</span><span class="special">-></span></code> where it makes sense). An attempt to
|
Clearly, we need a better idiom.
|
||||||
extract the contained value of an uninitialized optional object is an <span class="emphasis"><em>undefined
|
|
||||||
behaviour</em></span> (UB). This implementation guards the call with <code class="computeroutput"><span class="identifier">BOOST_ASSERT</span></code>. Therefore you should be sure
|
|
||||||
that the contained value is there before extracting. For instance, the following
|
|
||||||
code is reasonably UB-safe:
|
|
||||||
</p>
|
|
||||||
<pre class="programlisting"><span class="keyword">int</span> <span class="identifier">i</span> <span class="special">=</span> <span class="special">*</span><span class="identifier">convert</span><span class="special">(</span><span class="string">"100"</span><span class="special">);</span>
|
|
||||||
</pre>
|
|
||||||
<p>
|
|
||||||
This is because we know that string value <code class="computeroutput"><span class="string">"100"</span></code>
|
|
||||||
converts to a valid value of <code class="computeroutput"><span class="keyword">int</span></code>.
|
|
||||||
If you do not like this potential UB, you can use an alternative way of extracting
|
|
||||||
the contained value:
|
|
||||||
</p>
|
|
||||||
<pre class="programlisting"><span class="keyword">try</span> <span class="special">{</span>
|
|
||||||
<span class="keyword">int</span> <span class="identifier">j</span> <span class="special">=</span> <span class="identifier">convert</span><span class="special">(</span><span class="identifier">text</span><span class="special">).</span><span class="identifier">value</span><span class="special">();</span>
|
|
||||||
<span class="special">}</span>
|
|
||||||
<span class="keyword">catch</span> <span class="special">(</span><span class="keyword">const</span> <span class="identifier">boost</span><span class="special">::</span><span class="identifier">bad_optional_access</span><span class="special">&)</span> <span class="special">{</span>
|
|
||||||
<span class="comment">// deal with it</span>
|
|
||||||
<span class="special">}</span>
|
|
||||||
</pre>
|
|
||||||
<p>
|
|
||||||
This version throws an exception upon an attempt to access a non-existent
|
|
||||||
contained value. If your way of dealing with the missing value is to use
|
|
||||||
some default, like <code class="computeroutput"><span class="number">0</span></code>, there exists
|
|
||||||
a yet another alternative:
|
|
||||||
</p>
|
|
||||||
<pre class="programlisting"><span class="keyword">int</span> <span class="identifier">k</span> <span class="special">=</span> <span class="identifier">convert</span><span class="special">(</span><span class="identifier">text</span><span class="special">).</span><span class="identifier">value_or</span><span class="special">(</span><span class="number">0</span><span class="special">);</span>
|
|
||||||
</pre>
|
|
||||||
<p>
|
|
||||||
This uses the <code class="computeroutput"><span class="identifier">atoi</span></code>-like approach
|
|
||||||
to conversions: if <code class="computeroutput"><span class="identifier">text</span></code> does
|
|
||||||
not represent an integral number just return <code class="computeroutput"><span class="number">0</span></code>.
|
|
||||||
Now, let's consider how function <code class="computeroutput"><span class="identifier">convert</span></code>
|
|
||||||
can be implemented.
|
|
||||||
</p>
|
|
||||||
<pre class="programlisting"><span class="identifier">boost</span><span class="special">::</span><span class="identifier">optionl</span><span class="special"><</span><span class="keyword">int</span><span class="special">></span> <span class="identifier">convert</span><span class="special">(</span><span class="keyword">const</span> <span class="identifier">std</span><span class="special">::</span><span class="identifier">string</span><span class="special">&</span> <span class="identifier">text</span><span class="special">)</span>
|
|
||||||
<span class="special">{</span>
|
|
||||||
<span class="identifier">std</span><span class="special">::</span><span class="identifier">stringstream</span> <span class="identifier">s</span><span class="special">(</span><span class="identifier">text</span><span class="special">);</span>
|
|
||||||
<span class="keyword">int</span> <span class="identifier">i</span><span class="special">;</span>
|
|
||||||
<span class="keyword">if</span> <span class="special">((</span><span class="identifier">s</span> <span class="special">>></span> <span class="identifier">i</span><span class="special">)</span> <span class="special">&&</span> <span class="identifier">s</span><span class="special">.</span><span class="identifier">get</span><span class="special">()</span> <span class="special">==</span> <span class="identifier">std</span><span class="special">::</span><span class="identifier">char_traits</span><span class="special"><</span><span class="keyword">char</span><span class="special">>::</span><span class="identifier">eof</span><span class="special">())</span>
|
|
||||||
<span class="keyword">return</span> <span class="identifier">i</span><span class="special">;</span>
|
|
||||||
<span class="keyword">else</span>
|
|
||||||
<span class="keyword">return</span> <span class="identifier">boost</span><span class="special">::</span><span class="identifier">none</span><span class="special">;</span>
|
|
||||||
<span class="special">}</span>
|
|
||||||
</pre>
|
|
||||||
<p>
|
|
||||||
Observe the two return statements. <code class="computeroutput"><span class="keyword">return</span>
|
|
||||||
<span class="identifier">i</span></code> uses the converting constructor
|
|
||||||
that can create <code class="computeroutput"><span class="identifier">optional</span><span class="special"><</span><span class="identifier">T</span><span class="special">></span></code>
|
|
||||||
from <code class="computeroutput"><span class="identifier">T</span></code>. Thus constructed
|
|
||||||
optional object is initialized and its value is a copy of <code class="computeroutput"><span class="identifier">i</span></code>.
|
|
||||||
The other return statement uses another converting constructor from a special
|
|
||||||
tag <code class="computeroutput"><span class="identifier">boost</span><span class="special">::</span><span class="identifier">none</span></code>. It is used to indicate that we want
|
|
||||||
to create an uninitialized optional object.
|
|
||||||
</p>
|
</p>
|
||||||
</div>
|
</div>
|
||||||
<div class="section">
|
<div class="section">
|
||||||
<div class="titlepage"><div><div><h3 class="title">
|
<div class="titlepage"><div><div><h3 class="title">
|
||||||
<a name="boost_optional.tutorial.optional_data_members"></a><a class="link" href="tutorial.html#boost_optional.tutorial.optional_data_members" title="Optional data members">Optional
|
<a name="boost_optional.tutorial.design_overview"></a><a class="link" href="tutorial.html#boost_optional.tutorial.design_overview" title="Design Overview">Design Overview</a>
|
||||||
data members</a>
|
|
||||||
</h3></div></div></div>
|
</h3></div></div></div>
|
||||||
|
<div class="toc"><dl class="toc">
|
||||||
|
<dt><span class="section"><a href="tutorial.html#boost_optional.tutorial.design_overview.the_models">The
|
||||||
|
models</a></span></dt>
|
||||||
|
<dt><span class="section"><a href="tutorial.html#boost_optional.tutorial.design_overview.the_semantics">The
|
||||||
|
semantics</a></span></dt>
|
||||||
|
<dt><span class="section"><a href="tutorial.html#boost_optional.tutorial.design_overview.the_interface">The
|
||||||
|
Interface</a></span></dt>
|
||||||
|
</dl></div>
|
||||||
|
<div class="section">
|
||||||
|
<div class="titlepage"><div><div><h4 class="title">
|
||||||
|
<a name="boost_optional.tutorial.design_overview.the_models"></a><a class="link" href="tutorial.html#boost_optional.tutorial.design_overview.the_models" title="The models">The
|
||||||
|
models</a>
|
||||||
|
</h4></div></div></div>
|
||||||
<p>
|
<p>
|
||||||
Suppose we want to implement a <span class="emphasis"><em>lazy load</em></span> optimization.
|
In C++, we can <span class="emphasis"><em>declare</em></span> an object (a variable) of type
|
||||||
This is because we do not want to perform an expensive initialization of
|
<code class="computeroutput"><span class="identifier">T</span></code>, and we can give this
|
||||||
our <code class="computeroutput"><span class="identifier">Resource</span></code> until (if at
|
variable an <span class="emphasis"><em>initial value</em></span> (through an <span class="emphasis"><em>initializer</em></span>.
|
||||||
all) it is really used. We can do it this way:
|
(cf. 8.5)). When a declaration includes a non-empty initializer (an initial
|
||||||
</p>
|
value is given), it is said that the object has been initialized. If the
|
||||||
<pre class="programlisting"><span class="keyword">class</span> <span class="identifier">Widget</span>
|
declaration uses an empty initializer (no initial value is given), and
|
||||||
<span class="special">{</span>
|
neither default nor value initialization applies, it is said that the object
|
||||||
<span class="identifier">boost</span><span class="special">::</span><span class="identifier">optional</span><span class="special"><</span><span class="identifier">Resource</span><span class="special">></span> <span class="identifier">resource_</span><span class="special">;</span>
|
is <span class="bold"><strong>uninitialized</strong></span>. Its actual value exist
|
||||||
|
but has an <span class="emphasis"><em>indeterminate initial value</em></span> (cf. 8.5/11).
|
||||||
<span class="keyword">public</span><span class="special">:</span>
|
<code class="computeroutput"><span class="identifier">optional</span><span class="special"><</span><span class="identifier">T</span><span class="special">></span></code>
|
||||||
<span class="identifier">Widget</span><span class="special">()</span> <span class="special">{}</span>
|
intends to formalize the notion of initialization (or lack of it) allowing
|
||||||
|
a program to test whether an object has been initialized and stating that
|
||||||
<span class="identifier">Resource</span><span class="special">&</span> <span class="identifier">getResource</span><span class="special">()</span> <span class="comment">// not thread-safe</span>
|
access to the value of an uninitialized object is undefined behavior. That
|
||||||
<span class="special">{</span>
|
is, when a variable is declared as <code class="computeroutput"><span class="identifier">optional</span><span class="special"><</span><span class="identifier">T</span><span class="special">></span></code> and no initial value is given, the
|
||||||
<span class="keyword">if</span> <span class="special">(</span><span class="identifier">resource_</span> <span class="special">==</span> <span class="identifier">boost</span><span class="special">::</span><span class="identifier">none</span><span class="special">)</span>
|
variable is <span class="emphasis"><em>formally</em></span> uninitialized. A formally uninitialized
|
||||||
<span class="identifier">resource_</span><span class="special">.</span><span class="identifier">emplace</span><span class="special">(</span><span class="string">"resource"</span><span class="special">,</span> <span class="string">"arguments"</span><span class="special">);</span>
|
optional object has conceptually no value at all and this situation can
|
||||||
|
be tested at runtime. It is formally <span class="emphasis"><em>undefined behavior</em></span>
|
||||||
<span class="keyword">return</span> <span class="special">*</span><span class="identifier">resource_</span><span class="special">;</span>
|
to try to access the value of an uninitialized optional. An uninitialized
|
||||||
<span class="special">}</span>
|
optional can be assigned a value, in which case its initialization state
|
||||||
<span class="special">};</span>
|
changes to initialized. Furthermore, given the formal treatment of initialization
|
||||||
</pre>
|
states in optional objects, it is even possible to reset an optional to
|
||||||
|
<span class="emphasis"><em>uninitialized</em></span>.
|
||||||
|
</p>
|
||||||
<p>
|
<p>
|
||||||
<code class="computeroutput"><span class="identifier">optional</span></code>'s default constructor
|
In C++ there is no formal notion of uninitialized objects, which means
|
||||||
creates an uninitialized optional. No call to <code class="computeroutput"><span class="identifier">Resource</span></code>'s
|
that objects always have an initial value even if indeterminate. As discussed
|
||||||
default constructor is attempted. <code class="computeroutput"><span class="identifier">Resource</span></code>
|
on the previous section, this has a drawback because you need additional
|
||||||
doesn't have to be <a href="http://www.sgi.com/tech/stl/DefaultConstructible.html" target="_top">Default
|
information to tell if an object has been effectively initialized. One
|
||||||
Constructible</a>. In function <code class="computeroutput"><span class="identifier">getResource</span></code>
|
of the typical ways in which this has been historically dealt with is via
|
||||||
we first check if <code class="computeroutput"><span class="identifier">resource_</span></code>
|
a special value: <code class="computeroutput"><span class="identifier">EOF</span></code>,
|
||||||
is initialized. This time we do not use the contextual conversion to <code class="computeroutput"><span class="keyword">bool</span></code>, but a comparison with <code class="computeroutput"><span class="identifier">boost</span><span class="special">::</span><span class="identifier">none</span></code>. These two ways are equivalent. Function
|
<code class="computeroutput"><span class="identifier">npos</span></code>, -1, etc... This is
|
||||||
<code class="computeroutput"><span class="identifier">emplace</span></code> initializes the optional
|
equivalent to adding the special value to the set of possible values of
|
||||||
in-place by perfect-forwarding the arguments to the constructor of <code class="computeroutput"><span class="identifier">Resource</span></code>. No copy- or move-construction
|
a given type. This super set of <code class="computeroutput"><span class="identifier">T</span></code>
|
||||||
is involved here. <code class="computeroutput"><span class="identifier">Resource</span></code>
|
plus some <span class="emphasis"><em>nil_t</em></span>—where <code class="computeroutput"><span class="identifier">nil_t</span></code>
|
||||||
doesn't even have to be <code class="computeroutput"><span class="identifier">MoveConstructible</span></code>.
|
is some stateless POD—can be modeled in modern languages as a <span class="bold"><strong>discriminated union</strong></span> of T and nil_t. Discriminated
|
||||||
</p>
|
unions are often called <span class="emphasis"><em>variants</em></span>. A variant has a
|
||||||
<div class="note"><table border="0" summary="Note">
|
<span class="emphasis"><em>current type</em></span>, which in our case is either <code class="computeroutput"><span class="identifier">T</span></code> or <code class="computeroutput"><span class="identifier">nil_t</span></code>.
|
||||||
|
Using the <a href="../../../../variant/index.html" target="_top">Boost.Variant</a>
|
||||||
|
library, this model can be implemented in terms of <code class="computeroutput"><span class="identifier">boost</span><span class="special">::</span><span class="identifier">variant</span><span class="special"><</span><span class="identifier">T</span><span class="special">,</span><span class="identifier">nil_t</span><span class="special">></span></code>. There is precedent for a discriminated
|
||||||
|
union as a model for an optional value: the <a href="http://www.haskell.org/" target="_top">Haskell</a>
|
||||||
|
<span class="bold"><strong>Maybe</strong></span> built-in type constructor. Thus,
|
||||||
|
a discriminated union <code class="computeroutput"><span class="identifier">T</span><span class="special">+</span><span class="identifier">nil_t</span></code>
|
||||||
|
serves as a conceptual foundation.
|
||||||
|
</p>
|
||||||
|
<p>
|
||||||
|
A <code class="computeroutput"><span class="identifier">variant</span><span class="special"><</span><span class="identifier">T</span><span class="special">,</span><span class="identifier">nil_t</span><span class="special">></span></code> follows naturally from the traditional
|
||||||
|
idiom of extending the range of possible values adding an additional sentinel
|
||||||
|
value with the special meaning of <span class="emphasis"><em>Nothing</em></span>. However,
|
||||||
|
this additional <span class="emphasis"><em>Nothing</em></span> value is largely irrelevant
|
||||||
|
for our purpose since our goal is to formalize the notion of uninitialized
|
||||||
|
objects and, while a special extended value can be used to convey that
|
||||||
|
meaning, it is not strictly necessary in order to do so.
|
||||||
|
</p>
|
||||||
|
<p>
|
||||||
|
The observation made in the last paragraph about the irrelevant nature
|
||||||
|
of the additional <code class="computeroutput"><span class="identifier">nil_t</span></code>
|
||||||
|
with respect to <span class="underline">purpose</span> of <code class="computeroutput"><span class="identifier">optional</span><span class="special"><</span><span class="identifier">T</span><span class="special">></span></code>
|
||||||
|
suggests an alternative model: a <span class="emphasis"><em>container</em></span> that either
|
||||||
|
has a value of <code class="computeroutput"><span class="identifier">T</span></code> or nothing.
|
||||||
|
</p>
|
||||||
|
<p>
|
||||||
|
As of this writing I don't know of any precedent for a variable-size fixed-capacity
|
||||||
|
(of 1) stack-based container model for optional values, yet I believe this
|
||||||
|
is the consequence of the lack of practical implementations of such a container
|
||||||
|
rather than an inherent shortcoming of the container model.
|
||||||
|
</p>
|
||||||
|
<p>
|
||||||
|
In any event, both the discriminated-union or the single-element container
|
||||||
|
models serve as a conceptual ground for a class representing optional—i.e.
|
||||||
|
possibly uninitialized—objects. For instance, these models show the
|
||||||
|
<span class="emphasis"><em>exact</em></span> semantics required for a wrapper of optional
|
||||||
|
values:
|
||||||
|
</p>
|
||||||
|
<p>
|
||||||
|
Discriminated-union:
|
||||||
|
</p>
|
||||||
|
<div class="itemizedlist"><ul class="itemizedlist" style="list-style-type: disc; ">
|
||||||
|
<li class="listitem">
|
||||||
|
<span class="bold"><strong>deep-copy</strong></span> semantics: copies of the
|
||||||
|
variant implies copies of the value.
|
||||||
|
</li>
|
||||||
|
<li class="listitem">
|
||||||
|
<span class="bold"><strong>deep-relational</strong></span> semantics: comparisons
|
||||||
|
between variants matches both current types and values
|
||||||
|
</li>
|
||||||
|
<li class="listitem">
|
||||||
|
If the variant's current type is <code class="computeroutput"><span class="identifier">T</span></code>,
|
||||||
|
it is modeling an <span class="emphasis"><em>initialized</em></span> optional.
|
||||||
|
</li>
|
||||||
|
<li class="listitem">
|
||||||
|
If the variant's current type is not <code class="computeroutput"><span class="identifier">T</span></code>,
|
||||||
|
it is modeling an <span class="emphasis"><em>uninitialized</em></span> optional.
|
||||||
|
</li>
|
||||||
|
<li class="listitem">
|
||||||
|
Testing if the variant's current type is <code class="computeroutput"><span class="identifier">T</span></code>
|
||||||
|
models testing if the optional is initialized
|
||||||
|
</li>
|
||||||
|
<li class="listitem">
|
||||||
|
Trying to extract a <code class="computeroutput"><span class="identifier">T</span></code>
|
||||||
|
from a variant when its current type is not <code class="computeroutput"><span class="identifier">T</span></code>,
|
||||||
|
models the undefined behavior of trying to access the value of an uninitialized
|
||||||
|
optional
|
||||||
|
</li>
|
||||||
|
</ul></div>
|
||||||
|
<p>
|
||||||
|
Single-element container:
|
||||||
|
</p>
|
||||||
|
<div class="itemizedlist"><ul class="itemizedlist" style="list-style-type: disc; ">
|
||||||
|
<li class="listitem">
|
||||||
|
<span class="bold"><strong>deep-copy</strong></span> semantics: copies of the
|
||||||
|
container implies copies of the value.
|
||||||
|
</li>
|
||||||
|
<li class="listitem">
|
||||||
|
<span class="bold"><strong>deep-relational</strong></span> semantics: comparisons
|
||||||
|
between containers compare container size and if match, contained value
|
||||||
|
</li>
|
||||||
|
<li class="listitem">
|
||||||
|
If the container is not empty (contains an object of type <code class="computeroutput"><span class="identifier">T</span></code>), it is modeling an <span class="emphasis"><em>initialized</em></span>
|
||||||
|
optional.
|
||||||
|
</li>
|
||||||
|
<li class="listitem">
|
||||||
|
If the container is empty, it is modeling an <span class="emphasis"><em>uninitialized</em></span>
|
||||||
|
optional.
|
||||||
|
</li>
|
||||||
|
<li class="listitem">
|
||||||
|
Testing if the container is empty models testing if the optional is
|
||||||
|
initialized
|
||||||
|
</li>
|
||||||
|
<li class="listitem">
|
||||||
|
Trying to extract a <code class="computeroutput"><span class="identifier">T</span></code>
|
||||||
|
from an empty container models the undefined behavior of trying to
|
||||||
|
access the value of an uninitialized optional
|
||||||
|
</li>
|
||||||
|
</ul></div>
|
||||||
|
</div>
|
||||||
|
<div class="section">
|
||||||
|
<div class="titlepage"><div><div><h4 class="title">
|
||||||
|
<a name="boost_optional.tutorial.design_overview.the_semantics"></a><a class="link" href="tutorial.html#boost_optional.tutorial.design_overview.the_semantics" title="The semantics">The
|
||||||
|
semantics</a>
|
||||||
|
</h4></div></div></div>
|
||||||
|
<p>
|
||||||
|
Objects of type <code class="computeroutput"><span class="identifier">optional</span><span class="special"><</span><span class="identifier">T</span><span class="special">></span></code> are intended to be used in places where
|
||||||
|
objects of type <code class="computeroutput"><span class="identifier">T</span></code> would
|
||||||
|
but which might be uninitialized. Hence, <code class="computeroutput"><span class="identifier">optional</span><span class="special"><</span><span class="identifier">T</span><span class="special">></span></code>'s purpose is to formalize the additional
|
||||||
|
possibly uninitialized state. From the perspective of this role, <code class="computeroutput"><span class="identifier">optional</span><span class="special"><</span><span class="identifier">T</span><span class="special">></span></code>
|
||||||
|
can have the same operational semantics of <code class="computeroutput"><span class="identifier">T</span></code>
|
||||||
|
plus the additional semantics corresponding to this special state. As such,
|
||||||
|
<code class="computeroutput"><span class="identifier">optional</span><span class="special"><</span><span class="identifier">T</span><span class="special">></span></code>
|
||||||
|
could be thought of as a <span class="emphasis"><em>supertype</em></span> of <code class="computeroutput"><span class="identifier">T</span></code>. Of course, we can't do that in C++,
|
||||||
|
so we need to compose the desired semantics using a different mechanism.
|
||||||
|
Doing it the other way around, that is, making <code class="computeroutput"><span class="identifier">optional</span><span class="special"><</span><span class="identifier">T</span><span class="special">></span></code> a <span class="emphasis"><em>subtype</em></span> of
|
||||||
|
<code class="computeroutput"><span class="identifier">T</span></code> is not only conceptually
|
||||||
|
wrong but also impractical: it is not allowed to derive from a non-class
|
||||||
|
type, such as a built-in type.
|
||||||
|
</p>
|
||||||
|
<p>
|
||||||
|
We can draw from the purpose of <code class="computeroutput"><span class="identifier">optional</span><span class="special"><</span><span class="identifier">T</span><span class="special">></span></code> the required basic semantics:
|
||||||
|
</p>
|
||||||
|
<div class="itemizedlist"><ul class="itemizedlist" style="list-style-type: disc; ">
|
||||||
|
<li class="listitem">
|
||||||
|
<span class="bold"><strong>Default Construction:</strong></span> To introduce
|
||||||
|
a formally uninitialized wrapped object.
|
||||||
|
</li>
|
||||||
|
<li class="listitem">
|
||||||
|
<span class="bold"><strong>Direct Value Construction via copy:</strong></span>
|
||||||
|
To introduce a formally initialized wrapped object whose value is obtained
|
||||||
|
as a copy of some object.
|
||||||
|
</li>
|
||||||
|
<li class="listitem">
|
||||||
|
<span class="bold"><strong>Deep Copy Construction:</strong></span> To obtain
|
||||||
|
a new yet equivalent wrapped object.
|
||||||
|
</li>
|
||||||
|
<li class="listitem">
|
||||||
|
<span class="bold"><strong>Direct Value Assignment (upon initialized):</strong></span>
|
||||||
|
To assign a value to the wrapped object.
|
||||||
|
</li>
|
||||||
|
<li class="listitem">
|
||||||
|
<span class="bold"><strong>Direct Value Assignment (upon uninitialized):</strong></span>
|
||||||
|
To initialize the wrapped object with a value obtained as a copy of
|
||||||
|
some object.
|
||||||
|
</li>
|
||||||
|
<li class="listitem">
|
||||||
|
<span class="bold"><strong>Assignment (upon initialized):</strong></span> To
|
||||||
|
assign to the wrapped object the value of another wrapped object.
|
||||||
|
</li>
|
||||||
|
<li class="listitem">
|
||||||
|
<span class="bold"><strong>Assignment (upon uninitialized):</strong></span> To
|
||||||
|
initialize the wrapped object with value of another wrapped object.
|
||||||
|
</li>
|
||||||
|
<li class="listitem">
|
||||||
|
<span class="bold"><strong>Deep Relational Operations (when supported by
|
||||||
|
the type T):</strong></span> To compare wrapped object values taking into
|
||||||
|
account the presence of uninitialized states.
|
||||||
|
</li>
|
||||||
|
<li class="listitem">
|
||||||
|
<span class="bold"><strong>Value access:</strong></span> To unwrap the wrapped
|
||||||
|
object.
|
||||||
|
</li>
|
||||||
|
<li class="listitem">
|
||||||
|
<span class="bold"><strong>Initialization state query:</strong></span> To determine
|
||||||
|
if the object is formally initialized or not.
|
||||||
|
</li>
|
||||||
|
<li class="listitem">
|
||||||
|
<span class="bold"><strong>Swap:</strong></span> To exchange wrapped objects.
|
||||||
|
(with whatever exception safety guarantees are provided by <code class="computeroutput"><span class="identifier">T</span></code>'s swap).
|
||||||
|
</li>
|
||||||
|
<li class="listitem">
|
||||||
|
<span class="bold"><strong>De-initialization:</strong></span> To release the
|
||||||
|
wrapped object (if any) and leave the wrapper in the uninitialized
|
||||||
|
state.
|
||||||
|
</li>
|
||||||
|
</ul></div>
|
||||||
|
<p>
|
||||||
|
Additional operations are useful, such as converting constructors and converting
|
||||||
|
assignments, in-place construction and assignment, and safe value access
|
||||||
|
via a pointer to the wrapped object or null.
|
||||||
|
</p>
|
||||||
|
</div>
|
||||||
|
<div class="section">
|
||||||
|
<div class="titlepage"><div><div><h4 class="title">
|
||||||
|
<a name="boost_optional.tutorial.design_overview.the_interface"></a><a class="link" href="tutorial.html#boost_optional.tutorial.design_overview.the_interface" title="The Interface">The
|
||||||
|
Interface</a>
|
||||||
|
</h4></div></div></div>
|
||||||
|
<p>
|
||||||
|
Since the purpose of optional is to allow us to use objects with a formal
|
||||||
|
uninitialized additional state, the interface could try to follow the interface
|
||||||
|
of the underlying <code class="computeroutput"><span class="identifier">T</span></code> type
|
||||||
|
as much as possible. In order to choose the proper degree of adoption of
|
||||||
|
the native <code class="computeroutput"><span class="identifier">T</span></code> interface,
|
||||||
|
the following must be noted: Even if all the operations supported by an
|
||||||
|
instance of type <code class="computeroutput"><span class="identifier">T</span></code> are
|
||||||
|
defined for the entire range of values for such a type, an <code class="computeroutput"><span class="identifier">optional</span><span class="special"><</span><span class="identifier">T</span><span class="special">></span></code>
|
||||||
|
extends such a set of values with a new value for which most (otherwise
|
||||||
|
valid) operations are not defined in terms of <code class="computeroutput"><span class="identifier">T</span></code>.
|
||||||
|
</p>
|
||||||
|
<p>
|
||||||
|
Furthermore, since <code class="computeroutput"><span class="identifier">optional</span><span class="special"><</span><span class="identifier">T</span><span class="special">></span></code> itself is merely a <code class="computeroutput"><span class="identifier">T</span></code>
|
||||||
|
wrapper (modeling a <code class="computeroutput"><span class="identifier">T</span></code> supertype),
|
||||||
|
any attempt to define such operations upon uninitialized optionals will
|
||||||
|
be totally artificial w.r.t. <code class="computeroutput"><span class="identifier">T</span></code>.
|
||||||
|
</p>
|
||||||
|
<p>
|
||||||
|
This library chooses an interface which follows from <code class="computeroutput"><span class="identifier">T</span></code>'s
|
||||||
|
interface only for those operations which are well defined (w.r.t the type
|
||||||
|
<code class="computeroutput"><span class="identifier">T</span></code>) even if any of the operands
|
||||||
|
are uninitialized. These operations include: construction, copy-construction,
|
||||||
|
assignment, swap and relational operations.
|
||||||
|
</p>
|
||||||
|
<p>
|
||||||
|
For the value access operations, which are undefined (w.r.t the type <code class="computeroutput"><span class="identifier">T</span></code>) when the operand is uninitialized,
|
||||||
|
a different interface is chosen (which will be explained next).
|
||||||
|
</p>
|
||||||
|
<p>
|
||||||
|
Also, the presence of the possibly uninitialized state requires additional
|
||||||
|
operations not provided by <code class="computeroutput"><span class="identifier">T</span></code>
|
||||||
|
itself which are supported by a special interface.
|
||||||
|
</p>
|
||||||
|
<h6>
|
||||||
|
<a name="boost_optional.tutorial.design_overview.the_interface.h0"></a>
|
||||||
|
<span class="phrase"><a name="boost_optional.tutorial.design_overview.the_interface.lexically_hinted_value_access_in_the_presence_of_possibly_untitialized_optional_objects__the_operators___and___gt_"></a></span><a class="link" href="tutorial.html#boost_optional.tutorial.design_overview.the_interface.lexically_hinted_value_access_in_the_presence_of_possibly_untitialized_optional_objects__the_operators___and___gt_">Lexically-hinted
|
||||||
|
Value Access in the presence of possibly untitialized optional objects:
|
||||||
|
The operators * and -></a>
|
||||||
|
</h6>
|
||||||
|
<p>
|
||||||
|
A relevant feature of a pointer is that it can have a <span class="bold"><strong>null
|
||||||
|
pointer value</strong></span>. This is a <span class="emphasis"><em>special</em></span> value
|
||||||
|
which is used to indicate that the pointer is not referring to any object
|
||||||
|
at all. In other words, null pointer values convey the notion of nonexistent
|
||||||
|
objects.
|
||||||
|
</p>
|
||||||
|
<p>
|
||||||
|
This meaning of the null pointer value allowed pointers to became a <span class="emphasis"><em>de
|
||||||
|
facto</em></span> standard for handling optional objects because all you
|
||||||
|
have to do to refer to a value which you don't really have is to use a
|
||||||
|
null pointer value of the appropriate type. Pointers have been used for
|
||||||
|
decades—from the days of C APIs to modern C++ libraries—to <span class="emphasis"><em>refer</em></span>
|
||||||
|
to optional (that is, possibly nonexistent) objects; particularly as optional
|
||||||
|
arguments to a function, but also quite often as optional data members.
|
||||||
|
</p>
|
||||||
|
<p>
|
||||||
|
The possible presence of a null pointer value makes the operations that
|
||||||
|
access the pointee's value possibly undefined, therefore, expressions which
|
||||||
|
use dereference and access operators, such as: <code class="computeroutput"><span class="special">(</span>
|
||||||
|
<span class="special">*</span><span class="identifier">p</span>
|
||||||
|
<span class="special">=</span> <span class="number">2</span> <span class="special">)</span></code> and <code class="computeroutput"><span class="special">(</span>
|
||||||
|
<span class="identifier">p</span><span class="special">-></span><span class="identifier">foo</span><span class="special">()</span> <span class="special">)</span></code>, implicitly convey the notion of optionality,
|
||||||
|
and this information is tied to the <span class="emphasis"><em>syntax</em></span> of the
|
||||||
|
expressions. That is, the presence of operators <code class="computeroutput"><span class="special">*</span></code>
|
||||||
|
and <code class="computeroutput"><span class="special">-></span></code> tell by themselves
|
||||||
|
—without any additional context— that the expression will be undefined
|
||||||
|
unless the implied pointee actually exist.
|
||||||
|
</p>
|
||||||
|
<p>
|
||||||
|
Such a <span class="emphasis"><em>de facto</em></span> idiom for referring to optional objects
|
||||||
|
can be formalized in the form of a concept: the <a href="../../../../utility/OptionalPointee.html" target="_top">OptionalPointee</a>
|
||||||
|
concept. This concept captures the syntactic usage of operators <code class="computeroutput"><span class="special">*</span></code>, <code class="computeroutput"><span class="special">-></span></code>
|
||||||
|
and contextual conversion to <code class="computeroutput"><span class="keyword">bool</span></code>
|
||||||
|
to convey the notion of optionality.
|
||||||
|
</p>
|
||||||
|
<p>
|
||||||
|
However, pointers are good to <span class="underline">refer</span>
|
||||||
|
to optional objects, but not particularly good to handle the optional objects
|
||||||
|
in all other respects, such as initializing or moving/copying them. The
|
||||||
|
problem resides in the shallow-copy of pointer semantics: if you need to
|
||||||
|
effectively move or copy the object, pointers alone are not enough. The
|
||||||
|
problem is that copies of pointers do not imply copies of pointees. For
|
||||||
|
example, as was discussed in the motivation, pointers alone cannot be used
|
||||||
|
to return optional objects from a function because the object must move
|
||||||
|
outside from the function and into the caller's context.
|
||||||
|
</p>
|
||||||
|
<p>
|
||||||
|
A solution to the shallow-copy problem that is often used is to resort
|
||||||
|
to dynamic allocation and use a smart pointer to automatically handle the
|
||||||
|
details of this. For example, if a function is to optionally return an
|
||||||
|
object <code class="computeroutput"><span class="identifier">X</span></code>, it can use <code class="computeroutput"><span class="identifier">shared_ptr</span><span class="special"><</span><span class="identifier">X</span><span class="special">></span></code>
|
||||||
|
as the return value. However, this requires dynamic allocation of <code class="computeroutput"><span class="identifier">X</span></code>. If <code class="computeroutput"><span class="identifier">X</span></code>
|
||||||
|
is a built-in or small POD, this technique is very poor in terms of required
|
||||||
|
resources. Optional objects are essentially values so it is very convenient
|
||||||
|
to be able to use automatic storage and deep-copy semantics to manipulate
|
||||||
|
optional values just as we do with ordinary values. Pointers do not have
|
||||||
|
this semantics, so are inappropriate for the initialization and transport
|
||||||
|
of optional values, yet are quite convenient for handling the access to
|
||||||
|
the possible undefined value because of the idiomatic aid present in the
|
||||||
|
<a href="../../../../utility/OptionalPointee.html" target="_top">OptionalPointee</a>
|
||||||
|
concept incarnated by pointers.
|
||||||
|
</p>
|
||||||
|
<h6>
|
||||||
|
<a name="boost_optional.tutorial.design_overview.the_interface.h1"></a>
|
||||||
|
<span class="phrase"><a name="boost_optional.tutorial.design_overview.the_interface.optional_lt_t_gt__as_a_model_of_optionalpointee"></a></span><a class="link" href="tutorial.html#boost_optional.tutorial.design_overview.the_interface.optional_lt_t_gt__as_a_model_of_optionalpointee">Optional<T>
|
||||||
|
as a model of OptionalPointee</a>
|
||||||
|
</h6>
|
||||||
|
<p>
|
||||||
|
For value access operations <code class="computeroutput"><span class="identifier">optional</span><span class="special"><></span></code> uses operators <code class="computeroutput"><span class="special">*</span></code>
|
||||||
|
and <code class="computeroutput"><span class="special">-></span></code> to lexically warn
|
||||||
|
about the possibly uninitialized state appealing to the familiar pointer
|
||||||
|
semantics w.r.t. to null pointers.
|
||||||
|
</p>
|
||||||
|
<div class="warning"><table border="0" summary="Warning">
|
||||||
<tr>
|
<tr>
|
||||||
<td rowspan="2" align="center" valign="top" width="25"><img alt="[Note]" src="../../../../../doc/src/images/note.png"></td>
|
<td rowspan="2" align="center" valign="top" width="25"><img alt="[Warning]" src="../../../../../doc/src/images/warning.png"></td>
|
||||||
<th align="left">Note</th>
|
<th align="left">Warning</th>
|
||||||
</tr>
|
</tr>
|
||||||
<tr><td align="left" valign="top"><p>
|
<tr><td align="left" valign="top"><p>
|
||||||
Function <code class="computeroutput"><span class="identifier">emplace</span></code> is only
|
However, it is particularly important to note that <code class="computeroutput"><span class="identifier">optional</span><span class="special"><></span></code> objects are not pointers. <span class="underline"><code class="computeroutput"><span class="identifier">optional</span><span class="special"><></span></code> is not, and does not model, a
|
||||||
available on compilers that support rvalue references and variadic templates.
|
pointer</span>.
|
||||||
If your compiler does not support these features and you still need to
|
</p></td></tr>
|
||||||
avoid any move-constructions, use <a class="link" href="in_place_factories.html" title="In-Place Factories">In-Place
|
|
||||||
Factories</a>.
|
|
||||||
</p></td></tr>
|
|
||||||
</table></div>
|
</table></div>
|
||||||
|
<p>
|
||||||
|
For instance, <code class="computeroutput"><span class="identifier">optional</span><span class="special"><></span></code> does not have shallow-copy so does
|
||||||
|
not alias: two different optionals never refer to the <span class="emphasis"><em>same</em></span>
|
||||||
|
value unless <code class="computeroutput"><span class="identifier">T</span></code> itself is
|
||||||
|
a reference (but may have <span class="emphasis"><em>equivalent</em></span> values). The
|
||||||
|
difference between an <code class="computeroutput"><span class="identifier">optional</span><span class="special"><</span><span class="identifier">T</span><span class="special">></span></code> and a pointer must be kept in mind,
|
||||||
|
particularly because the semantics of relational operators are different:
|
||||||
|
since <code class="computeroutput"><span class="identifier">optional</span><span class="special"><</span><span class="identifier">T</span><span class="special">></span></code>
|
||||||
|
is a value-wrapper, relational operators are deep: they compare optional
|
||||||
|
values; but relational operators for pointers are shallow: they do not
|
||||||
|
compare pointee values. As a result, you might be able to replace <code class="computeroutput"><span class="identifier">optional</span><span class="special"><</span><span class="identifier">T</span><span class="special">></span></code>
|
||||||
|
by <code class="computeroutput"><span class="identifier">T</span><span class="special">*</span></code>
|
||||||
|
on some situations but not always. Specifically, on generic code written
|
||||||
|
for both, you cannot use relational operators directly, and must use the
|
||||||
|
template functions <a href="../../../../utility/OptionalPointee.html#equal" target="_top"><code class="computeroutput"><span class="identifier">equal_pointees</span><span class="special">()</span></code></a>
|
||||||
|
and <a href="../../../../utility/OptionalPointee.html#less" target="_top"><code class="computeroutput"><span class="identifier">less_pointees</span><span class="special">()</span></code></a>
|
||||||
|
instead.
|
||||||
|
</p>
|
||||||
</div>
|
</div>
|
||||||
<div class="section">
|
|
||||||
<div class="titlepage"><div><div><h3 class="title">
|
|
||||||
<a name="boost_optional.tutorial.bypassing_unnecessary_default_construction"></a><a class="link" href="tutorial.html#boost_optional.tutorial.bypassing_unnecessary_default_construction" title="Bypassing unnecessary default construction">Bypassing
|
|
||||||
unnecessary default construction</a>
|
|
||||||
</h3></div></div></div>
|
|
||||||
<p>
|
|
||||||
Suppose we have class <code class="computeroutput"><span class="identifier">Date</span></code>,
|
|
||||||
which does not have a default constructor: there is no good candidate for
|
|
||||||
a default date. We have a function that returns two dates in form of a <code class="computeroutput"><span class="identifier">boost</span><span class="special">::</span><span class="identifier">tuple</span></code>:
|
|
||||||
</p>
|
|
||||||
<pre class="programlisting"><span class="identifier">boost</span><span class="special">::</span><span class="identifier">tuple</span><span class="special"><</span><span class="identifier">Date</span><span class="special">,</span> <span class="identifier">Date</span><span class="special">></span> <span class="identifier">getPeriod</span><span class="special">();</span>
|
|
||||||
</pre>
|
|
||||||
<p>
|
|
||||||
In other place we want to use the result of <code class="computeroutput"><span class="identifier">getPeriod</span></code>,
|
|
||||||
but want the two dates to be named: <code class="computeroutput"><span class="identifier">begin</span></code>
|
|
||||||
and <code class="computeroutput"><span class="identifier">end</span></code>. We want to implement
|
|
||||||
something like 'multiple return values':
|
|
||||||
</p>
|
|
||||||
<pre class="programlisting"><span class="identifier">Date</span> <span class="identifier">begin</span><span class="special">,</span> <span class="identifier">end</span><span class="special">;</span> <span class="comment">// Error: no default ctor!</span>
|
|
||||||
<span class="identifier">boost</span><span class="special">::</span><span class="identifier">tie</span><span class="special">(</span><span class="identifier">begin</span><span class="special">,</span> <span class="identifier">end</span><span class="special">)</span> <span class="special">=</span> <span class="identifier">getPeriod</span><span class="special">();</span>
|
|
||||||
</pre>
|
|
||||||
<p>
|
|
||||||
The second line works already, this is the capability of Boost.Tuple library,
|
|
||||||
but the first line won't work. We could set some initial invented dates,
|
|
||||||
but it is confusing and may be an unacceptable cost, given that these values
|
|
||||||
will be overwritten in the next line anyway. This is where <code class="computeroutput"><span class="identifier">optional</span></code> can help:
|
|
||||||
</p>
|
|
||||||
<pre class="programlisting"><span class="identifier">boost</span><span class="special">::</span><span class="identifier">optional</span><span class="special"><</span><span class="identifier">Date</span><span class="special">></span> <span class="identifier">begin</span><span class="special">,</span> <span class="identifier">end</span><span class="special">;</span>
|
|
||||||
<span class="identifier">boost</span><span class="special">::</span><span class="identifier">tie</span><span class="special">(</span><span class="identifier">begin</span><span class="special">,</span> <span class="identifier">end</span><span class="special">)</span> <span class="special">=</span> <span class="identifier">getPeriod</span><span class="special">();</span>
|
|
||||||
</pre>
|
|
||||||
<p>
|
|
||||||
It works because inside <code class="computeroutput"><span class="identifier">boost</span><span class="special">::</span><span class="identifier">tie</span></code> a
|
|
||||||
move-assignment from <code class="computeroutput"><span class="identifier">T</span></code> is
|
|
||||||
invoked on <code class="computeroutput"><span class="identifier">optional</span><span class="special"><</span><span class="identifier">T</span><span class="special">></span></code>,
|
|
||||||
which internally calls a move-constructor of <code class="computeroutput"><span class="identifier">T</span></code>.
|
|
||||||
</p>
|
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
<table xmlns:rev="http://www.cs.rpi.edu/~gregod/boost/tools/doc/revision" width="100%"><tr>
|
<table xmlns:rev="http://www.cs.rpi.edu/~gregod/boost/tools/doc/revision" width="100%"><tr>
|
||||||
@ -233,7 +517,7 @@
|
|||||||
</tr></table>
|
</tr></table>
|
||||||
<hr>
|
<hr>
|
||||||
<div class="spirit-nav">
|
<div class="spirit-nav">
|
||||||
<a accesskey="p" href="../index.html"><img src="../../../../../doc/src/images/prev.png" alt="Prev"></a><a accesskey="u" href="../index.html"><img src="../../../../../doc/src/images/up.png" alt="Up"></a><a accesskey="h" href="../index.html"><img src="../../../../../doc/src/images/home.png" alt="Home"></a><a accesskey="n" href="discussion.html"><img src="../../../../../doc/src/images/next.png" alt="Next"></a>
|
<a accesskey="p" href="quick_start.html"><img src="../../../../../doc/src/images/prev.png" alt="Prev"></a><a accesskey="u" href="../index.html"><img src="../../../../../doc/src/images/up.png" alt="Up"></a><a accesskey="h" href="../index.html"><img src="../../../../../doc/src/images/home.png" alt="Home"></a><a accesskey="n" href="synopsis.html"><img src="../../../../../doc/src/images/next.png" alt="Next"></a>
|
||||||
</div>
|
</div>
|
||||||
</body>
|
</body>
|
||||||
</html>
|
</html>
|
||||||
|
@ -0,0 +1,108 @@
|
|||||||
|
<html>
|
||||||
|
<head>
|
||||||
|
<meta http-equiv="Content-Type" content="text/html; charset=US-ASCII">
|
||||||
|
<title>A note about optional<bool></title>
|
||||||
|
<link rel="stylesheet" href="../../../../../../doc/src/boostbook.css" type="text/css">
|
||||||
|
<meta name="generator" content="DocBook XSL Stylesheets V1.78.1">
|
||||||
|
<link rel="home" href="../../index.html" title="Chapter 1. Boost.Optional">
|
||||||
|
<link rel="up" href="../../optional/tutorial.html" title="Tutorial">
|
||||||
|
<link rel="prev" href="in_place_factories.html" title="In-Place Factories">
|
||||||
|
<link rel="next" href="exception_safety_guarantees.html" title="Exception Safety Guarantees">
|
||||||
|
</head>
|
||||||
|
<body bgcolor="white" text="black" link="#0000FF" vlink="#840084" alink="#0000FF">
|
||||||
|
<table cellpadding="2" width="100%"><tr>
|
||||||
|
<td valign="top"><img alt="Boost C++ Libraries" width="277" height="86" src="../../../../../../boost.png"></td>
|
||||||
|
<td align="center"><a href="../../../../../../index.html">Home</a></td>
|
||||||
|
<td align="center"><a href="../../../../../../libs/libraries.htm">Libraries</a></td>
|
||||||
|
<td align="center"><a href="http://www.boost.org/users/people.html">People</a></td>
|
||||||
|
<td align="center"><a href="http://www.boost.org/users/faq.html">FAQ</a></td>
|
||||||
|
<td align="center"><a href="../../../../../../more/index.htm">More</a></td>
|
||||||
|
</tr></table>
|
||||||
|
<hr>
|
||||||
|
<div class="spirit-nav">
|
||||||
|
<a accesskey="p" href="in_place_factories.html"><img src="../../../../../../doc/src/images/prev.png" alt="Prev"></a><a accesskey="u" href="../../optional/tutorial.html"><img src="../../../../../../doc/src/images/up.png" alt="Up"></a><a accesskey="h" href="../../index.html"><img src="../../../../../../doc/src/images/home.png" alt="Home"></a><a accesskey="n" href="exception_safety_guarantees.html"><img src="../../../../../../doc/src/images/next.png" alt="Next"></a>
|
||||||
|
</div>
|
||||||
|
<div class="section">
|
||||||
|
<div class="titlepage"><div><div><h3 class="title">
|
||||||
|
<a name="boost_optional.tutorial.a_note_about_optional_bool_"></a><a class="link" href="a_note_about_optional_bool_.html" title="A note about optional<bool>">A
|
||||||
|
note about optional<bool></a>
|
||||||
|
</h3></div></div></div>
|
||||||
|
<p>
|
||||||
|
<code class="computeroutput"><span class="identifier">optional</span><span class="special"><</span><span class="keyword">bool</span><span class="special">></span></code> should
|
||||||
|
be used with special caution and consideration.
|
||||||
|
</p>
|
||||||
|
<p>
|
||||||
|
First, it is functionally similar to a tristate boolean (false, maybe, true)
|
||||||
|
—such as <a href="../../../../../../doc/html/tribool.html" target="_top">boost::tribool</a>—
|
||||||
|
except that in a tristate boolean, the maybe state <span class="underline">represents
|
||||||
|
a valid value</span>, unlike the corresponding state of an uninitialized
|
||||||
|
<code class="computeroutput"><span class="identifier">optional</span><span class="special"><</span><span class="keyword">bool</span><span class="special">></span></code>.
|
||||||
|
It should be carefully considered if an <code class="computeroutput"><span class="identifier">optional</span><span class="special"><</span><span class="keyword">bool</span><span class="special">></span></code>
|
||||||
|
instead of a <code class="computeroutput"><span class="identifier">tribool</span></code> is really
|
||||||
|
needed.
|
||||||
|
</p>
|
||||||
|
<p>
|
||||||
|
Second, although <code class="computeroutput"><span class="identifier">optional</span><span class="special"><></span></code> provides a contextual conversion
|
||||||
|
to <code class="computeroutput"><span class="keyword">bool</span></code> in C++11, this falls
|
||||||
|
back to an implicit conversion on older compilers. This conversion refers
|
||||||
|
to the initialization state and not to the contained value. Using <code class="computeroutput"><span class="identifier">optional</span><span class="special"><</span><span class="keyword">bool</span><span class="special">></span></code> can
|
||||||
|
lead to subtle errors due to the implicit <code class="computeroutput"><span class="keyword">bool</span></code>
|
||||||
|
conversion:
|
||||||
|
</p>
|
||||||
|
<pre class="programlisting"><span class="keyword">void</span> <span class="identifier">foo</span> <span class="special">(</span> <span class="keyword">bool</span> <span class="identifier">v</span> <span class="special">)</span> <span class="special">;</span>
|
||||||
|
<span class="keyword">void</span> <span class="identifier">bar</span><span class="special">()</span>
|
||||||
|
<span class="special">{</span>
|
||||||
|
<span class="identifier">optional</span><span class="special"><</span><span class="keyword">bool</span><span class="special">></span> <span class="identifier">v</span> <span class="special">=</span> <span class="keyword">try</span><span class="special">();</span>
|
||||||
|
|
||||||
|
<span class="comment">// The following intended to pass the value of 'v' to foo():</span>
|
||||||
|
<span class="identifier">foo</span><span class="special">(</span><span class="identifier">v</span><span class="special">);</span>
|
||||||
|
<span class="comment">// But instead, the initialization state is passed</span>
|
||||||
|
<span class="comment">// due to a typo: it should have been foo(*v).</span>
|
||||||
|
<span class="special">}</span>
|
||||||
|
</pre>
|
||||||
|
<p>
|
||||||
|
The only implicit conversion is to <code class="computeroutput"><span class="keyword">bool</span></code>,
|
||||||
|
and it is safe in the sense that typical integral promotions don't apply
|
||||||
|
(i.e. if <code class="computeroutput"><span class="identifier">foo</span><span class="special">()</span></code>
|
||||||
|
takes an <code class="computeroutput"><span class="keyword">int</span></code> instead, it won't
|
||||||
|
compile).
|
||||||
|
</p>
|
||||||
|
<p>
|
||||||
|
Third, mixed comparisons with <code class="computeroutput"><span class="keyword">bool</span></code>
|
||||||
|
work differently than similar mixed comparisons between pointers and <code class="computeroutput"><span class="keyword">bool</span></code>, so the results might surprise you:
|
||||||
|
</p>
|
||||||
|
<pre class="programlisting"><span class="identifier">optional</span><span class="special"><</span><span class="keyword">bool</span><span class="special">></span> <span class="identifier">oEmpty</span><span class="special">(</span><span class="identifier">none</span><span class="special">),</span> <span class="identifier">oTrue</span><span class="special">(</span><span class="keyword">true</span><span class="special">),</span> <span class="identifier">oFalse</span><span class="special">(</span><span class="keyword">false</span><span class="special">);</span>
|
||||||
|
|
||||||
|
<span class="keyword">if</span> <span class="special">(</span><span class="identifier">oEmpty</span> <span class="special">==</span> <span class="identifier">none</span><span class="special">);</span> <span class="comment">// renders true</span>
|
||||||
|
<span class="keyword">if</span> <span class="special">(</span><span class="identifier">oEmpty</span> <span class="special">==</span> <span class="keyword">false</span><span class="special">);</span> <span class="comment">// renders false!</span>
|
||||||
|
<span class="keyword">if</span> <span class="special">(</span><span class="identifier">oEmpty</span> <span class="special">==</span> <span class="keyword">true</span><span class="special">);</span> <span class="comment">// renders false!</span>
|
||||||
|
|
||||||
|
<span class="keyword">if</span> <span class="special">(</span><span class="identifier">oFalse</span> <span class="special">==</span> <span class="identifier">none</span><span class="special">);</span> <span class="comment">// renders false</span>
|
||||||
|
<span class="keyword">if</span> <span class="special">(</span><span class="identifier">oFalse</span> <span class="special">==</span> <span class="keyword">false</span><span class="special">);</span> <span class="comment">// renders true!</span>
|
||||||
|
<span class="keyword">if</span> <span class="special">(</span><span class="identifier">oFalse</span> <span class="special">==</span> <span class="keyword">true</span><span class="special">);</span> <span class="comment">// renders false</span>
|
||||||
|
|
||||||
|
<span class="keyword">if</span> <span class="special">(</span><span class="identifier">oTrue</span> <span class="special">==</span> <span class="identifier">none</span><span class="special">);</span> <span class="comment">// renders false</span>
|
||||||
|
<span class="keyword">if</span> <span class="special">(</span><span class="identifier">oTrue</span> <span class="special">==</span> <span class="keyword">false</span><span class="special">);</span> <span class="comment">// renders false</span>
|
||||||
|
<span class="keyword">if</span> <span class="special">(</span><span class="identifier">oTrue</span> <span class="special">==</span> <span class="keyword">true</span><span class="special">);</span> <span class="comment">// renders true</span>
|
||||||
|
</pre>
|
||||||
|
<p>
|
||||||
|
In other words, for <code class="computeroutput"><span class="identifier">optional</span><span class="special"><></span></code>, the following assertion does not
|
||||||
|
hold:
|
||||||
|
</p>
|
||||||
|
<pre class="programlisting"><span class="identifier">assert</span><span class="special">((</span><span class="identifier">opt</span> <span class="special">==</span> <span class="keyword">false</span><span class="special">)</span> <span class="special">==</span> <span class="special">(!</span><span class="identifier">opt</span><span class="special">));</span>
|
||||||
|
</pre>
|
||||||
|
</div>
|
||||||
|
<table xmlns:rev="http://www.cs.rpi.edu/~gregod/boost/tools/doc/revision" width="100%"><tr>
|
||||||
|
<td align="left"></td>
|
||||||
|
<td align="right"><div class="copyright-footer">Copyright © 2003-2007 Fernando Luis Cacciola Carballal<br>Copyright © 2014 Andrzej Krzemieński<p>
|
||||||
|
Distributed under the Boost Software License, Version 1.0. (See accompanying
|
||||||
|
file LICENSE_1_0.txt or copy at <a href="http://www.boost.org/LICENSE_1_0.txt" target="_top">http://www.boost.org/LICENSE_1_0.txt</a>)
|
||||||
|
</p>
|
||||||
|
</div></td>
|
||||||
|
</tr></table>
|
||||||
|
<hr>
|
||||||
|
<div class="spirit-nav">
|
||||||
|
<a accesskey="p" href="in_place_factories.html"><img src="../../../../../../doc/src/images/prev.png" alt="Prev"></a><a accesskey="u" href="../../optional/tutorial.html"><img src="../../../../../../doc/src/images/up.png" alt="Up"></a><a accesskey="h" href="../../index.html"><img src="../../../../../../doc/src/images/home.png" alt="Home"></a><a accesskey="n" href="exception_safety_guarantees.html"><img src="../../../../../../doc/src/images/next.png" alt="Next"></a>
|
||||||
|
</div>
|
||||||
|
</body>
|
||||||
|
</html>
|
423
doc/html/boost_optional/tutorial/design_overview.html
Normal file
423
doc/html/boost_optional/tutorial/design_overview.html
Normal file
@ -0,0 +1,423 @@
|
|||||||
|
<html>
|
||||||
|
<head>
|
||||||
|
<meta http-equiv="Content-Type" content="text/html; charset=US-ASCII">
|
||||||
|
<title>Design Overview</title>
|
||||||
|
<link rel="stylesheet" href="../../../../../../doc/src/boostbook.css" type="text/css">
|
||||||
|
<meta name="generator" content="DocBook XSL Stylesheets V1.78.1">
|
||||||
|
<link rel="home" href="../../index.html" title="Chapter 1. Boost.Optional">
|
||||||
|
<link rel="up" href="../../optional/tutorial.html" title="Tutorial">
|
||||||
|
<link rel="prev" href="motivation.html" title="Motivation">
|
||||||
|
<link rel="next" href="optional_references.html" title="Optional references">
|
||||||
|
</head>
|
||||||
|
<body bgcolor="white" text="black" link="#0000FF" vlink="#840084" alink="#0000FF">
|
||||||
|
<table cellpadding="2" width="100%"><tr>
|
||||||
|
<td valign="top"><img alt="Boost C++ Libraries" width="277" height="86" src="../../../../../../boost.png"></td>
|
||||||
|
<td align="center"><a href="../../../../../../index.html">Home</a></td>
|
||||||
|
<td align="center"><a href="../../../../../../libs/libraries.htm">Libraries</a></td>
|
||||||
|
<td align="center"><a href="http://www.boost.org/users/people.html">People</a></td>
|
||||||
|
<td align="center"><a href="http://www.boost.org/users/faq.html">FAQ</a></td>
|
||||||
|
<td align="center"><a href="../../../../../../more/index.htm">More</a></td>
|
||||||
|
</tr></table>
|
||||||
|
<hr>
|
||||||
|
<div class="spirit-nav">
|
||||||
|
<a accesskey="p" href="motivation.html"><img src="../../../../../../doc/src/images/prev.png" alt="Prev"></a><a accesskey="u" href="../../optional/tutorial.html"><img src="../../../../../../doc/src/images/up.png" alt="Up"></a><a accesskey="h" href="../../index.html"><img src="../../../../../../doc/src/images/home.png" alt="Home"></a><a accesskey="n" href="optional_references.html"><img src="../../../../../../doc/src/images/next.png" alt="Next"></a>
|
||||||
|
</div>
|
||||||
|
<div class="section">
|
||||||
|
<div class="titlepage"><div><div><h3 class="title">
|
||||||
|
<a name="boost_optional.tutorial.design_overview"></a><a class="link" href="design_overview.html" title="Design Overview">Design Overview</a>
|
||||||
|
</h3></div></div></div>
|
||||||
|
<div class="toc"><dl class="toc">
|
||||||
|
<dt><span class="section"><a href="design_overview.html#boost_optional.tutorial.design_overview.the_models">The
|
||||||
|
models</a></span></dt>
|
||||||
|
<dt><span class="section"><a href="design_overview.html#boost_optional.tutorial.design_overview.the_semantics">The
|
||||||
|
semantics</a></span></dt>
|
||||||
|
<dt><span class="section"><a href="design_overview.html#boost_optional.tutorial.design_overview.the_interface">The
|
||||||
|
Interface</a></span></dt>
|
||||||
|
</dl></div>
|
||||||
|
<div class="section">
|
||||||
|
<div class="titlepage"><div><div><h4 class="title">
|
||||||
|
<a name="boost_optional.tutorial.design_overview.the_models"></a><a class="link" href="design_overview.html#boost_optional.tutorial.design_overview.the_models" title="The models">The
|
||||||
|
models</a>
|
||||||
|
</h4></div></div></div>
|
||||||
|
<p>
|
||||||
|
In C++, we can <span class="emphasis"><em>declare</em></span> an object (a variable) of type
|
||||||
|
<code class="computeroutput"><span class="identifier">T</span></code>, and we can give this
|
||||||
|
variable an <span class="emphasis"><em>initial value</em></span> (through an <span class="emphasis"><em>initializer</em></span>.
|
||||||
|
(cf. 8.5)). When a declaration includes a non-empty initializer (an initial
|
||||||
|
value is given), it is said that the object has been initialized. If the
|
||||||
|
declaration uses an empty initializer (no initial value is given), and
|
||||||
|
neither default nor value initialization applies, it is said that the object
|
||||||
|
is <span class="bold"><strong>uninitialized</strong></span>. Its actual value exist
|
||||||
|
but has an <span class="emphasis"><em>indeterminate initial value</em></span> (cf. 8.5/11).
|
||||||
|
<code class="computeroutput"><span class="identifier">optional</span><span class="special"><</span><span class="identifier">T</span><span class="special">></span></code>
|
||||||
|
intends to formalize the notion of initialization (or lack of it) allowing
|
||||||
|
a program to test whether an object has been initialized and stating that
|
||||||
|
access to the value of an uninitialized object is undefined behavior. That
|
||||||
|
is, when a variable is declared as <code class="computeroutput"><span class="identifier">optional</span><span class="special"><</span><span class="identifier">T</span><span class="special">></span></code> and no initial value is given, the
|
||||||
|
variable is <span class="emphasis"><em>formally</em></span> uninitialized. A formally uninitialized
|
||||||
|
optional object has conceptually no value at all and this situation can
|
||||||
|
be tested at runtime. It is formally <span class="emphasis"><em>undefined behavior</em></span>
|
||||||
|
to try to access the value of an uninitialized optional. An uninitialized
|
||||||
|
optional can be assigned a value, in which case its initialization state
|
||||||
|
changes to initialized. Furthermore, given the formal treatment of initialization
|
||||||
|
states in optional objects, it is even possible to reset an optional to
|
||||||
|
<span class="emphasis"><em>uninitialized</em></span>.
|
||||||
|
</p>
|
||||||
|
<p>
|
||||||
|
In C++ there is no formal notion of uninitialized objects, which means
|
||||||
|
that objects always have an initial value even if indeterminate. As discussed
|
||||||
|
on the previous section, this has a drawback because you need additional
|
||||||
|
information to tell if an object has been effectively initialized. One
|
||||||
|
of the typical ways in which this has been historically dealt with is via
|
||||||
|
a special value: <code class="computeroutput"><span class="identifier">EOF</span></code>,
|
||||||
|
<code class="computeroutput"><span class="identifier">npos</span></code>, -1, etc... This is
|
||||||
|
equivalent to adding the special value to the set of possible values of
|
||||||
|
a given type. This super set of <code class="computeroutput"><span class="identifier">T</span></code>
|
||||||
|
plus some <span class="emphasis"><em>nil_t</em></span>—where <code class="computeroutput"><span class="identifier">nil_t</span></code>
|
||||||
|
is some stateless POD—can be modeled in modern languages as a <span class="bold"><strong>discriminated union</strong></span> of T and nil_t. Discriminated
|
||||||
|
unions are often called <span class="emphasis"><em>variants</em></span>. A variant has a
|
||||||
|
<span class="emphasis"><em>current type</em></span>, which in our case is either <code class="computeroutput"><span class="identifier">T</span></code> or <code class="computeroutput"><span class="identifier">nil_t</span></code>.
|
||||||
|
Using the <a href="../../../../../variant/index.html" target="_top">Boost.Variant</a>
|
||||||
|
library, this model can be implemented in terms of <code class="computeroutput"><span class="identifier">boost</span><span class="special">::</span><span class="identifier">variant</span><span class="special"><</span><span class="identifier">T</span><span class="special">,</span><span class="identifier">nil_t</span><span class="special">></span></code>. There is precedent for a discriminated
|
||||||
|
union as a model for an optional value: the <a href="http://www.haskell.org/" target="_top">Haskell</a>
|
||||||
|
<span class="bold"><strong>Maybe</strong></span> built-in type constructor. Thus,
|
||||||
|
a discriminated union <code class="computeroutput"><span class="identifier">T</span><span class="special">+</span><span class="identifier">nil_t</span></code>
|
||||||
|
serves as a conceptual foundation.
|
||||||
|
</p>
|
||||||
|
<p>
|
||||||
|
A <code class="computeroutput"><span class="identifier">variant</span><span class="special"><</span><span class="identifier">T</span><span class="special">,</span><span class="identifier">nil_t</span><span class="special">></span></code> follows naturally from the traditional
|
||||||
|
idiom of extending the range of possible values adding an additional sentinel
|
||||||
|
value with the special meaning of <span class="emphasis"><em>Nothing</em></span>. However,
|
||||||
|
this additional <span class="emphasis"><em>Nothing</em></span> value is largely irrelevant
|
||||||
|
for our purpose since our goal is to formalize the notion of uninitialized
|
||||||
|
objects and, while a special extended value can be used to convey that
|
||||||
|
meaning, it is not strictly necessary in order to do so.
|
||||||
|
</p>
|
||||||
|
<p>
|
||||||
|
The observation made in the last paragraph about the irrelevant nature
|
||||||
|
of the additional <code class="computeroutput"><span class="identifier">nil_t</span></code>
|
||||||
|
with respect to <span class="underline">purpose</span> of <code class="computeroutput"><span class="identifier">optional</span><span class="special"><</span><span class="identifier">T</span><span class="special">></span></code>
|
||||||
|
suggests an alternative model: a <span class="emphasis"><em>container</em></span> that either
|
||||||
|
has a value of <code class="computeroutput"><span class="identifier">T</span></code> or nothing.
|
||||||
|
</p>
|
||||||
|
<p>
|
||||||
|
As of this writing I don't know of any precedent for a variable-size fixed-capacity
|
||||||
|
(of 1) stack-based container model for optional values, yet I believe this
|
||||||
|
is the consequence of the lack of practical implementations of such a container
|
||||||
|
rather than an inherent shortcoming of the container model.
|
||||||
|
</p>
|
||||||
|
<p>
|
||||||
|
In any event, both the discriminated-union or the single-element container
|
||||||
|
models serve as a conceptual ground for a class representing optional—i.e.
|
||||||
|
possibly uninitialized—objects. For instance, these models show the
|
||||||
|
<span class="emphasis"><em>exact</em></span> semantics required for a wrapper of optional
|
||||||
|
values:
|
||||||
|
</p>
|
||||||
|
<p>
|
||||||
|
Discriminated-union:
|
||||||
|
</p>
|
||||||
|
<div class="itemizedlist"><ul class="itemizedlist" style="list-style-type: disc; ">
|
||||||
|
<li class="listitem">
|
||||||
|
<span class="bold"><strong>deep-copy</strong></span> semantics: copies of the
|
||||||
|
variant implies copies of the value.
|
||||||
|
</li>
|
||||||
|
<li class="listitem">
|
||||||
|
<span class="bold"><strong>deep-relational</strong></span> semantics: comparisons
|
||||||
|
between variants matches both current types and values
|
||||||
|
</li>
|
||||||
|
<li class="listitem">
|
||||||
|
If the variant's current type is <code class="computeroutput"><span class="identifier">T</span></code>,
|
||||||
|
it is modeling an <span class="emphasis"><em>initialized</em></span> optional.
|
||||||
|
</li>
|
||||||
|
<li class="listitem">
|
||||||
|
If the variant's current type is not <code class="computeroutput"><span class="identifier">T</span></code>,
|
||||||
|
it is modeling an <span class="emphasis"><em>uninitialized</em></span> optional.
|
||||||
|
</li>
|
||||||
|
<li class="listitem">
|
||||||
|
Testing if the variant's current type is <code class="computeroutput"><span class="identifier">T</span></code>
|
||||||
|
models testing if the optional is initialized
|
||||||
|
</li>
|
||||||
|
<li class="listitem">
|
||||||
|
Trying to extract a <code class="computeroutput"><span class="identifier">T</span></code>
|
||||||
|
from a variant when its current type is not <code class="computeroutput"><span class="identifier">T</span></code>,
|
||||||
|
models the undefined behavior of trying to access the value of an uninitialized
|
||||||
|
optional
|
||||||
|
</li>
|
||||||
|
</ul></div>
|
||||||
|
<p>
|
||||||
|
Single-element container:
|
||||||
|
</p>
|
||||||
|
<div class="itemizedlist"><ul class="itemizedlist" style="list-style-type: disc; ">
|
||||||
|
<li class="listitem">
|
||||||
|
<span class="bold"><strong>deep-copy</strong></span> semantics: copies of the
|
||||||
|
container implies copies of the value.
|
||||||
|
</li>
|
||||||
|
<li class="listitem">
|
||||||
|
<span class="bold"><strong>deep-relational</strong></span> semantics: comparisons
|
||||||
|
between containers compare container size and if match, contained value
|
||||||
|
</li>
|
||||||
|
<li class="listitem">
|
||||||
|
If the container is not empty (contains an object of type <code class="computeroutput"><span class="identifier">T</span></code>), it is modeling an <span class="emphasis"><em>initialized</em></span>
|
||||||
|
optional.
|
||||||
|
</li>
|
||||||
|
<li class="listitem">
|
||||||
|
If the container is empty, it is modeling an <span class="emphasis"><em>uninitialized</em></span>
|
||||||
|
optional.
|
||||||
|
</li>
|
||||||
|
<li class="listitem">
|
||||||
|
Testing if the container is empty models testing if the optional is
|
||||||
|
initialized
|
||||||
|
</li>
|
||||||
|
<li class="listitem">
|
||||||
|
Trying to extract a <code class="computeroutput"><span class="identifier">T</span></code>
|
||||||
|
from an empty container models the undefined behavior of trying to
|
||||||
|
access the value of an uninitialized optional
|
||||||
|
</li>
|
||||||
|
</ul></div>
|
||||||
|
</div>
|
||||||
|
<div class="section">
|
||||||
|
<div class="titlepage"><div><div><h4 class="title">
|
||||||
|
<a name="boost_optional.tutorial.design_overview.the_semantics"></a><a class="link" href="design_overview.html#boost_optional.tutorial.design_overview.the_semantics" title="The semantics">The
|
||||||
|
semantics</a>
|
||||||
|
</h4></div></div></div>
|
||||||
|
<p>
|
||||||
|
Objects of type <code class="computeroutput"><span class="identifier">optional</span><span class="special"><</span><span class="identifier">T</span><span class="special">></span></code> are intended to be used in places where
|
||||||
|
objects of type <code class="computeroutput"><span class="identifier">T</span></code> would
|
||||||
|
but which might be uninitialized. Hence, <code class="computeroutput"><span class="identifier">optional</span><span class="special"><</span><span class="identifier">T</span><span class="special">></span></code>'s purpose is to formalize the additional
|
||||||
|
possibly uninitialized state. From the perspective of this role, <code class="computeroutput"><span class="identifier">optional</span><span class="special"><</span><span class="identifier">T</span><span class="special">></span></code>
|
||||||
|
can have the same operational semantics of <code class="computeroutput"><span class="identifier">T</span></code>
|
||||||
|
plus the additional semantics corresponding to this special state. As such,
|
||||||
|
<code class="computeroutput"><span class="identifier">optional</span><span class="special"><</span><span class="identifier">T</span><span class="special">></span></code>
|
||||||
|
could be thought of as a <span class="emphasis"><em>supertype</em></span> of <code class="computeroutput"><span class="identifier">T</span></code>. Of course, we can't do that in C++,
|
||||||
|
so we need to compose the desired semantics using a different mechanism.
|
||||||
|
Doing it the other way around, that is, making <code class="computeroutput"><span class="identifier">optional</span><span class="special"><</span><span class="identifier">T</span><span class="special">></span></code> a <span class="emphasis"><em>subtype</em></span> of
|
||||||
|
<code class="computeroutput"><span class="identifier">T</span></code> is not only conceptually
|
||||||
|
wrong but also impractical: it is not allowed to derive from a non-class
|
||||||
|
type, such as a built-in type.
|
||||||
|
</p>
|
||||||
|
<p>
|
||||||
|
We can draw from the purpose of <code class="computeroutput"><span class="identifier">optional</span><span class="special"><</span><span class="identifier">T</span><span class="special">></span></code> the required basic semantics:
|
||||||
|
</p>
|
||||||
|
<div class="itemizedlist"><ul class="itemizedlist" style="list-style-type: disc; ">
|
||||||
|
<li class="listitem">
|
||||||
|
<span class="bold"><strong>Default Construction:</strong></span> To introduce
|
||||||
|
a formally uninitialized wrapped object.
|
||||||
|
</li>
|
||||||
|
<li class="listitem">
|
||||||
|
<span class="bold"><strong>Direct Value Construction via copy:</strong></span>
|
||||||
|
To introduce a formally initialized wrapped object whose value is obtained
|
||||||
|
as a copy of some object.
|
||||||
|
</li>
|
||||||
|
<li class="listitem">
|
||||||
|
<span class="bold"><strong>Deep Copy Construction:</strong></span> To obtain
|
||||||
|
a new yet equivalent wrapped object.
|
||||||
|
</li>
|
||||||
|
<li class="listitem">
|
||||||
|
<span class="bold"><strong>Direct Value Assignment (upon initialized):</strong></span>
|
||||||
|
To assign a value to the wrapped object.
|
||||||
|
</li>
|
||||||
|
<li class="listitem">
|
||||||
|
<span class="bold"><strong>Direct Value Assignment (upon uninitialized):</strong></span>
|
||||||
|
To initialize the wrapped object with a value obtained as a copy of
|
||||||
|
some object.
|
||||||
|
</li>
|
||||||
|
<li class="listitem">
|
||||||
|
<span class="bold"><strong>Assignment (upon initialized):</strong></span> To
|
||||||
|
assign to the wrapped object the value of another wrapped object.
|
||||||
|
</li>
|
||||||
|
<li class="listitem">
|
||||||
|
<span class="bold"><strong>Assignment (upon uninitialized):</strong></span> To
|
||||||
|
initialize the wrapped object with value of another wrapped object.
|
||||||
|
</li>
|
||||||
|
<li class="listitem">
|
||||||
|
<span class="bold"><strong>Deep Relational Operations (when supported by
|
||||||
|
the type T):</strong></span> To compare wrapped object values taking into
|
||||||
|
account the presence of uninitialized states.
|
||||||
|
</li>
|
||||||
|
<li class="listitem">
|
||||||
|
<span class="bold"><strong>Value access:</strong></span> To unwrap the wrapped
|
||||||
|
object.
|
||||||
|
</li>
|
||||||
|
<li class="listitem">
|
||||||
|
<span class="bold"><strong>Initialization state query:</strong></span> To determine
|
||||||
|
if the object is formally initialized or not.
|
||||||
|
</li>
|
||||||
|
<li class="listitem">
|
||||||
|
<span class="bold"><strong>Swap:</strong></span> To exchange wrapped objects.
|
||||||
|
(with whatever exception safety guarantees are provided by <code class="computeroutput"><span class="identifier">T</span></code>'s swap).
|
||||||
|
</li>
|
||||||
|
<li class="listitem">
|
||||||
|
<span class="bold"><strong>De-initialization:</strong></span> To release the
|
||||||
|
wrapped object (if any) and leave the wrapper in the uninitialized
|
||||||
|
state.
|
||||||
|
</li>
|
||||||
|
</ul></div>
|
||||||
|
<p>
|
||||||
|
Additional operations are useful, such as converting constructors and converting
|
||||||
|
assignments, in-place construction and assignment, and safe value access
|
||||||
|
via a pointer to the wrapped object or null.
|
||||||
|
</p>
|
||||||
|
</div>
|
||||||
|
<div class="section">
|
||||||
|
<div class="titlepage"><div><div><h4 class="title">
|
||||||
|
<a name="boost_optional.tutorial.design_overview.the_interface"></a><a class="link" href="design_overview.html#boost_optional.tutorial.design_overview.the_interface" title="The Interface">The
|
||||||
|
Interface</a>
|
||||||
|
</h4></div></div></div>
|
||||||
|
<p>
|
||||||
|
Since the purpose of optional is to allow us to use objects with a formal
|
||||||
|
uninitialized additional state, the interface could try to follow the interface
|
||||||
|
of the underlying <code class="computeroutput"><span class="identifier">T</span></code> type
|
||||||
|
as much as possible. In order to choose the proper degree of adoption of
|
||||||
|
the native <code class="computeroutput"><span class="identifier">T</span></code> interface,
|
||||||
|
the following must be noted: Even if all the operations supported by an
|
||||||
|
instance of type <code class="computeroutput"><span class="identifier">T</span></code> are
|
||||||
|
defined for the entire range of values for such a type, an <code class="computeroutput"><span class="identifier">optional</span><span class="special"><</span><span class="identifier">T</span><span class="special">></span></code>
|
||||||
|
extends such a set of values with a new value for which most (otherwise
|
||||||
|
valid) operations are not defined in terms of <code class="computeroutput"><span class="identifier">T</span></code>.
|
||||||
|
</p>
|
||||||
|
<p>
|
||||||
|
Furthermore, since <code class="computeroutput"><span class="identifier">optional</span><span class="special"><</span><span class="identifier">T</span><span class="special">></span></code> itself is merely a <code class="computeroutput"><span class="identifier">T</span></code>
|
||||||
|
wrapper (modeling a <code class="computeroutput"><span class="identifier">T</span></code> supertype),
|
||||||
|
any attempt to define such operations upon uninitialized optionals will
|
||||||
|
be totally artificial w.r.t. <code class="computeroutput"><span class="identifier">T</span></code>.
|
||||||
|
</p>
|
||||||
|
<p>
|
||||||
|
This library chooses an interface which follows from <code class="computeroutput"><span class="identifier">T</span></code>'s
|
||||||
|
interface only for those operations which are well defined (w.r.t the type
|
||||||
|
<code class="computeroutput"><span class="identifier">T</span></code>) even if any of the operands
|
||||||
|
are uninitialized. These operations include: construction, copy-construction,
|
||||||
|
assignment, swap and relational operations.
|
||||||
|
</p>
|
||||||
|
<p>
|
||||||
|
For the value access operations, which are undefined (w.r.t the type <code class="computeroutput"><span class="identifier">T</span></code>) when the operand is uninitialized,
|
||||||
|
a different interface is chosen (which will be explained next).
|
||||||
|
</p>
|
||||||
|
<p>
|
||||||
|
Also, the presence of the possibly uninitialized state requires additional
|
||||||
|
operations not provided by <code class="computeroutput"><span class="identifier">T</span></code>
|
||||||
|
itself which are supported by a special interface.
|
||||||
|
</p>
|
||||||
|
<h6>
|
||||||
|
<a name="boost_optional.tutorial.design_overview.the_interface.h0"></a>
|
||||||
|
<span class="phrase"><a name="boost_optional.tutorial.design_overview.the_interface.lexically_hinted_value_access_in_the_presence_of_possibly_untitialized_optional_objects__the_operators___and___gt_"></a></span><a class="link" href="design_overview.html#boost_optional.tutorial.design_overview.the_interface.lexically_hinted_value_access_in_the_presence_of_possibly_untitialized_optional_objects__the_operators___and___gt_">Lexically-hinted
|
||||||
|
Value Access in the presence of possibly untitialized optional objects:
|
||||||
|
The operators * and -></a>
|
||||||
|
</h6>
|
||||||
|
<p>
|
||||||
|
A relevant feature of a pointer is that it can have a <span class="bold"><strong>null
|
||||||
|
pointer value</strong></span>. This is a <span class="emphasis"><em>special</em></span> value
|
||||||
|
which is used to indicate that the pointer is not referring to any object
|
||||||
|
at all. In other words, null pointer values convey the notion of nonexistent
|
||||||
|
objects.
|
||||||
|
</p>
|
||||||
|
<p>
|
||||||
|
This meaning of the null pointer value allowed pointers to became a <span class="emphasis"><em>de
|
||||||
|
facto</em></span> standard for handling optional objects because all you
|
||||||
|
have to do to refer to a value which you don't really have is to use a
|
||||||
|
null pointer value of the appropriate type. Pointers have been used for
|
||||||
|
decades—from the days of C APIs to modern C++ libraries—to <span class="emphasis"><em>refer</em></span>
|
||||||
|
to optional (that is, possibly nonexistent) objects; particularly as optional
|
||||||
|
arguments to a function, but also quite often as optional data members.
|
||||||
|
</p>
|
||||||
|
<p>
|
||||||
|
The possible presence of a null pointer value makes the operations that
|
||||||
|
access the pointee's value possibly undefined, therefore, expressions which
|
||||||
|
use dereference and access operators, such as: <code class="computeroutput"><span class="special">(</span>
|
||||||
|
<span class="special">*</span><span class="identifier">p</span>
|
||||||
|
<span class="special">=</span> <span class="number">2</span> <span class="special">)</span></code> and <code class="computeroutput"><span class="special">(</span>
|
||||||
|
<span class="identifier">p</span><span class="special">-></span><span class="identifier">foo</span><span class="special">()</span> <span class="special">)</span></code>, implicitly convey the notion of optionality,
|
||||||
|
and this information is tied to the <span class="emphasis"><em>syntax</em></span> of the
|
||||||
|
expressions. That is, the presence of operators <code class="computeroutput"><span class="special">*</span></code>
|
||||||
|
and <code class="computeroutput"><span class="special">-></span></code> tell by themselves
|
||||||
|
—without any additional context— that the expression will be undefined
|
||||||
|
unless the implied pointee actually exist.
|
||||||
|
</p>
|
||||||
|
<p>
|
||||||
|
Such a <span class="emphasis"><em>de facto</em></span> idiom for referring to optional objects
|
||||||
|
can be formalized in the form of a concept: the <a href="../../../../../utility/OptionalPointee.html" target="_top">OptionalPointee</a>
|
||||||
|
concept. This concept captures the syntactic usage of operators <code class="computeroutput"><span class="special">*</span></code>, <code class="computeroutput"><span class="special">-></span></code>
|
||||||
|
and contextual conversion to <code class="computeroutput"><span class="keyword">bool</span></code>
|
||||||
|
to convey the notion of optionality.
|
||||||
|
</p>
|
||||||
|
<p>
|
||||||
|
However, pointers are good to <span class="underline">refer</span>
|
||||||
|
to optional objects, but not particularly good to handle the optional objects
|
||||||
|
in all other respects, such as initializing or moving/copying them. The
|
||||||
|
problem resides in the shallow-copy of pointer semantics: if you need to
|
||||||
|
effectively move or copy the object, pointers alone are not enough. The
|
||||||
|
problem is that copies of pointers do not imply copies of pointees. For
|
||||||
|
example, as was discussed in the motivation, pointers alone cannot be used
|
||||||
|
to return optional objects from a function because the object must move
|
||||||
|
outside from the function and into the caller's context.
|
||||||
|
</p>
|
||||||
|
<p>
|
||||||
|
A solution to the shallow-copy problem that is often used is to resort
|
||||||
|
to dynamic allocation and use a smart pointer to automatically handle the
|
||||||
|
details of this. For example, if a function is to optionally return an
|
||||||
|
object <code class="computeroutput"><span class="identifier">X</span></code>, it can use <code class="computeroutput"><span class="identifier">shared_ptr</span><span class="special"><</span><span class="identifier">X</span><span class="special">></span></code>
|
||||||
|
as the return value. However, this requires dynamic allocation of <code class="computeroutput"><span class="identifier">X</span></code>. If <code class="computeroutput"><span class="identifier">X</span></code>
|
||||||
|
is a built-in or small POD, this technique is very poor in terms of required
|
||||||
|
resources. Optional objects are essentially values so it is very convenient
|
||||||
|
to be able to use automatic storage and deep-copy semantics to manipulate
|
||||||
|
optional values just as we do with ordinary values. Pointers do not have
|
||||||
|
this semantics, so are inappropriate for the initialization and transport
|
||||||
|
of optional values, yet are quite convenient for handling the access to
|
||||||
|
the possible undefined value because of the idiomatic aid present in the
|
||||||
|
<a href="../../../../../utility/OptionalPointee.html" target="_top">OptionalPointee</a>
|
||||||
|
concept incarnated by pointers.
|
||||||
|
</p>
|
||||||
|
<h6>
|
||||||
|
<a name="boost_optional.tutorial.design_overview.the_interface.h1"></a>
|
||||||
|
<span class="phrase"><a name="boost_optional.tutorial.design_overview.the_interface.optional_lt_t_gt__as_a_model_of_optionalpointee"></a></span><a class="link" href="design_overview.html#boost_optional.tutorial.design_overview.the_interface.optional_lt_t_gt__as_a_model_of_optionalpointee">Optional<T>
|
||||||
|
as a model of OptionalPointee</a>
|
||||||
|
</h6>
|
||||||
|
<p>
|
||||||
|
For value access operations <code class="computeroutput"><span class="identifier">optional</span><span class="special"><></span></code> uses operators <code class="computeroutput"><span class="special">*</span></code>
|
||||||
|
and <code class="computeroutput"><span class="special">-></span></code> to lexically warn
|
||||||
|
about the possibly uninitialized state appealing to the familiar pointer
|
||||||
|
semantics w.r.t. to null pointers.
|
||||||
|
</p>
|
||||||
|
<div class="warning"><table border="0" summary="Warning">
|
||||||
|
<tr>
|
||||||
|
<td rowspan="2" align="center" valign="top" width="25"><img alt="[Warning]" src="../../../../../../doc/src/images/warning.png"></td>
|
||||||
|
<th align="left">Warning</th>
|
||||||
|
</tr>
|
||||||
|
<tr><td align="left" valign="top"><p>
|
||||||
|
However, it is particularly important to note that <code class="computeroutput"><span class="identifier">optional</span><span class="special"><></span></code> objects are not pointers. <span class="underline"><code class="computeroutput"><span class="identifier">optional</span><span class="special"><></span></code> is not, and does not model, a
|
||||||
|
pointer</span>.
|
||||||
|
</p></td></tr>
|
||||||
|
</table></div>
|
||||||
|
<p>
|
||||||
|
For instance, <code class="computeroutput"><span class="identifier">optional</span><span class="special"><></span></code> does not have shallow-copy so does
|
||||||
|
not alias: two different optionals never refer to the <span class="emphasis"><em>same</em></span>
|
||||||
|
value unless <code class="computeroutput"><span class="identifier">T</span></code> itself is
|
||||||
|
a reference (but may have <span class="emphasis"><em>equivalent</em></span> values). The
|
||||||
|
difference between an <code class="computeroutput"><span class="identifier">optional</span><span class="special"><</span><span class="identifier">T</span><span class="special">></span></code> and a pointer must be kept in mind,
|
||||||
|
particularly because the semantics of relational operators are different:
|
||||||
|
since <code class="computeroutput"><span class="identifier">optional</span><span class="special"><</span><span class="identifier">T</span><span class="special">></span></code>
|
||||||
|
is a value-wrapper, relational operators are deep: they compare optional
|
||||||
|
values; but relational operators for pointers are shallow: they do not
|
||||||
|
compare pointee values. As a result, you might be able to replace <code class="computeroutput"><span class="identifier">optional</span><span class="special"><</span><span class="identifier">T</span><span class="special">></span></code>
|
||||||
|
by <code class="computeroutput"><span class="identifier">T</span><span class="special">*</span></code>
|
||||||
|
on some situations but not always. Specifically, on generic code written
|
||||||
|
for both, you cannot use relational operators directly, and must use the
|
||||||
|
template functions <a href="../../../../../utility/OptionalPointee.html#equal" target="_top"><code class="computeroutput"><span class="identifier">equal_pointees</span><span class="special">()</span></code></a>
|
||||||
|
and <a href="../../../../../utility/OptionalPointee.html#less" target="_top"><code class="computeroutput"><span class="identifier">less_pointees</span><span class="special">()</span></code></a>
|
||||||
|
instead.
|
||||||
|
</p>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
<table xmlns:rev="http://www.cs.rpi.edu/~gregod/boost/tools/doc/revision" width="100%"><tr>
|
||||||
|
<td align="left"></td>
|
||||||
|
<td align="right"><div class="copyright-footer">Copyright © 2003-2007 Fernando Luis Cacciola Carballal<br>Copyright © 2014 Andrzej Krzemieński<p>
|
||||||
|
Distributed under the Boost Software License, Version 1.0. (See accompanying
|
||||||
|
file LICENSE_1_0.txt or copy at <a href="http://www.boost.org/LICENSE_1_0.txt" target="_top">http://www.boost.org/LICENSE_1_0.txt</a>)
|
||||||
|
</p>
|
||||||
|
</div></td>
|
||||||
|
</tr></table>
|
||||||
|
<hr>
|
||||||
|
<div class="spirit-nav">
|
||||||
|
<a accesskey="p" href="motivation.html"><img src="../../../../../../doc/src/images/prev.png" alt="Prev"></a><a accesskey="u" href="../../optional/tutorial.html"><img src="../../../../../../doc/src/images/up.png" alt="Up"></a><a accesskey="h" href="../../index.html"><img src="../../../../../../doc/src/images/home.png" alt="Home"></a><a accesskey="n" href="optional_references.html"><img src="../../../../../../doc/src/images/next.png" alt="Next"></a>
|
||||||
|
</div>
|
||||||
|
</body>
|
||||||
|
</html>
|
@ -0,0 +1,175 @@
|
|||||||
|
<html>
|
||||||
|
<head>
|
||||||
|
<meta http-equiv="Content-Type" content="text/html; charset=US-ASCII">
|
||||||
|
<title>Exception Safety Guarantees</title>
|
||||||
|
<link rel="stylesheet" href="../../../../../../doc/src/boostbook.css" type="text/css">
|
||||||
|
<meta name="generator" content="DocBook XSL Stylesheets V1.78.1">
|
||||||
|
<link rel="home" href="../../index.html" title="Chapter 1. Boost.Optional">
|
||||||
|
<link rel="up" href="../../optional/tutorial.html" title="Tutorial">
|
||||||
|
<link rel="prev" href="a_note_about_optional_bool_.html" title="A note about optional<bool>">
|
||||||
|
<link rel="next" href="type_requirements.html" title="Type requirements">
|
||||||
|
</head>
|
||||||
|
<body bgcolor="white" text="black" link="#0000FF" vlink="#840084" alink="#0000FF">
|
||||||
|
<table cellpadding="2" width="100%"><tr>
|
||||||
|
<td valign="top"><img alt="Boost C++ Libraries" width="277" height="86" src="../../../../../../boost.png"></td>
|
||||||
|
<td align="center"><a href="../../../../../../index.html">Home</a></td>
|
||||||
|
<td align="center"><a href="../../../../../../libs/libraries.htm">Libraries</a></td>
|
||||||
|
<td align="center"><a href="http://www.boost.org/users/people.html">People</a></td>
|
||||||
|
<td align="center"><a href="http://www.boost.org/users/faq.html">FAQ</a></td>
|
||||||
|
<td align="center"><a href="../../../../../../more/index.htm">More</a></td>
|
||||||
|
</tr></table>
|
||||||
|
<hr>
|
||||||
|
<div class="spirit-nav">
|
||||||
|
<a accesskey="p" href="a_note_about_optional_bool_.html"><img src="../../../../../../doc/src/images/prev.png" alt="Prev"></a><a accesskey="u" href="../../optional/tutorial.html"><img src="../../../../../../doc/src/images/up.png" alt="Up"></a><a accesskey="h" href="../../index.html"><img src="../../../../../../doc/src/images/home.png" alt="Home"></a><a accesskey="n" href="type_requirements.html"><img src="../../../../../../doc/src/images/next.png" alt="Next"></a>
|
||||||
|
</div>
|
||||||
|
<div class="section">
|
||||||
|
<div class="titlepage"><div><div><h3 class="title">
|
||||||
|
<a name="boost_optional.tutorial.exception_safety_guarantees"></a><a class="link" href="exception_safety_guarantees.html" title="Exception Safety Guarantees">Exception
|
||||||
|
Safety Guarantees</a>
|
||||||
|
</h3></div></div></div>
|
||||||
|
<p>
|
||||||
|
This library assumes that <code class="computeroutput"><span class="identifier">T</span></code>'s
|
||||||
|
destructor does not throw exceptions. If it does, the behaviour of many operations
|
||||||
|
on <code class="computeroutput"><span class="identifier">optional</span><span class="special"><</span><span class="identifier">T</span><span class="special">></span></code> is
|
||||||
|
undefined.
|
||||||
|
</p>
|
||||||
|
<p>
|
||||||
|
The following mutating operations never throw exceptions:
|
||||||
|
</p>
|
||||||
|
<div class="itemizedlist"><ul class="itemizedlist" style="list-style-type: disc; ">
|
||||||
|
<li class="listitem">
|
||||||
|
<code class="computeroutput"><span class="identifier">optional</span><span class="special"><</span><span class="identifier">T</span><span class="special">>::</span><span class="keyword">operator</span><span class="special">=</span> <span class="special">(</span> <span class="identifier">none_t</span>
|
||||||
|
<span class="special">)</span> <span class="keyword">noexcept</span></code>
|
||||||
|
</li>
|
||||||
|
<li class="listitem">
|
||||||
|
<code class="computeroutput"><span class="identifier">optional</span><span class="special"><</span><span class="identifier">T</span><span class="special">>::</span><span class="identifier">reset</span><span class="special">()</span> <span class="keyword">noexcept</span></code>
|
||||||
|
</li>
|
||||||
|
</ul></div>
|
||||||
|
<p>
|
||||||
|
In addition, the following constructors and the destructor never throw exceptions:
|
||||||
|
</p>
|
||||||
|
<div class="itemizedlist"><ul class="itemizedlist" style="list-style-type: disc; ">
|
||||||
|
<li class="listitem">
|
||||||
|
<code class="computeroutput"><span class="identifier">optional</span><span class="special"><</span><span class="identifier">T</span><span class="special">>::</span><span class="identifier">optional</span><span class="special">()</span>
|
||||||
|
<span class="keyword">noexcept</span></code>
|
||||||
|
</li>
|
||||||
|
<li class="listitem">
|
||||||
|
<code class="computeroutput"><span class="identifier">optional</span><span class="special"><</span><span class="identifier">T</span><span class="special">>::</span><span class="identifier">optional</span><span class="special">(</span>
|
||||||
|
<span class="identifier">none_t</span> <span class="special">)</span>
|
||||||
|
<span class="keyword">noexcept</span></code>
|
||||||
|
</li>
|
||||||
|
</ul></div>
|
||||||
|
<p>
|
||||||
|
Regarding the following assignment functions:
|
||||||
|
</p>
|
||||||
|
<div class="itemizedlist"><ul class="itemizedlist" style="list-style-type: disc; ">
|
||||||
|
<li class="listitem">
|
||||||
|
<code class="computeroutput"><span class="identifier">optional</span><span class="special"><</span><span class="identifier">T</span><span class="special">>::</span><span class="keyword">operator</span><span class="special">=</span> <span class="special">(</span> <span class="identifier">optional</span><span class="special"><</span><span class="identifier">T</span><span class="special">></span> <span class="keyword">const</span><span class="special">&</span> <span class="special">)</span></code>
|
||||||
|
</li>
|
||||||
|
<li class="listitem">
|
||||||
|
<code class="computeroutput"><span class="identifier">optional</span><span class="special"><</span><span class="identifier">T</span><span class="special">>::</span><span class="keyword">operator</span><span class="special">=</span> <span class="special">(</span> <span class="identifier">T</span> <span class="keyword">const</span><span class="special">&</span> <span class="special">)</span></code>
|
||||||
|
</li>
|
||||||
|
<li class="listitem">
|
||||||
|
<code class="computeroutput"><span class="keyword">template</span><span class="special"><</span><span class="keyword">class</span> <span class="identifier">U</span><span class="special">></span> <span class="identifier">optional</span><span class="special"><</span><span class="identifier">T</span><span class="special">>::</span><span class="keyword">operator</span><span class="special">=</span> <span class="special">(</span> <span class="identifier">optional</span><span class="special"><</span><span class="identifier">U</span><span class="special">></span> <span class="keyword">const</span><span class="special">&</span> <span class="special">)</span></code>
|
||||||
|
</li>
|
||||||
|
<li class="listitem">
|
||||||
|
<code class="computeroutput"><span class="keyword">template</span><span class="special"><</span><span class="keyword">class</span> <span class="identifier">InPlaceFactory</span><span class="special">></span> <span class="identifier">optional</span><span class="special"><</span><span class="identifier">T</span><span class="special">>::</span><span class="keyword">operator</span><span class="special">=</span> <span class="special">(</span> <span class="identifier">InPlaceFactory</span>
|
||||||
|
<span class="keyword">const</span><span class="special">&</span>
|
||||||
|
<span class="special">)</span></code>
|
||||||
|
</li>
|
||||||
|
<li class="listitem">
|
||||||
|
<code class="computeroutput"><span class="keyword">template</span><span class="special"><</span><span class="keyword">class</span> <span class="identifier">TypedInPlaceFactory</span><span class="special">></span> <span class="identifier">optional</span><span class="special"><</span><span class="identifier">T</span><span class="special">>::</span><span class="keyword">operator</span><span class="special">=</span> <span class="special">(</span> <span class="identifier">TypedInPlaceFactory</span>
|
||||||
|
<span class="keyword">const</span><span class="special">&</span>
|
||||||
|
<span class="special">)</span> </code>
|
||||||
|
</li>
|
||||||
|
<li class="listitem">
|
||||||
|
<code class="computeroutput"><span class="identifier">optional</span><span class="special"><</span><span class="identifier">T</span><span class="special">>::</span><span class="identifier">reset</span><span class="special">(</span> <span class="identifier">T</span> <span class="keyword">const</span><span class="special">&</span> <span class="special">)</span></code>
|
||||||
|
</li>
|
||||||
|
</ul></div>
|
||||||
|
<p>
|
||||||
|
They forward calls to the corresponding <code class="computeroutput"><span class="identifier">T</span></code>'s
|
||||||
|
constructors or assignments (depending on whether the optional object is
|
||||||
|
initialized or not); so if both <code class="computeroutput"><span class="identifier">T</span></code>'s
|
||||||
|
constructor and the assignment provide strong exception safety guarantee,
|
||||||
|
<code class="computeroutput"><span class="identifier">optional</span><span class="special"><</span><span class="identifier">T</span><span class="special">></span></code>'s
|
||||||
|
assignment also provides strong exception safety guarantee; otherwise we
|
||||||
|
only get the basic guarantee. Additionally, if both involved <code class="computeroutput"><span class="identifier">T</span></code>'s constructor and the assignment never
|
||||||
|
throw, <code class="computeroutput"><span class="identifier">optional</span><span class="special"><</span><span class="identifier">T</span><span class="special">></span></code>'s
|
||||||
|
assignment also never throws.
|
||||||
|
</p>
|
||||||
|
<p>
|
||||||
|
Unless <code class="computeroutput"><span class="identifier">T</span></code>'s constructor or
|
||||||
|
assignment throws, assignments to <code class="computeroutput"><span class="identifier">optional</span><span class="special"><</span><span class="identifier">T</span><span class="special">></span></code>
|
||||||
|
do not throw anything else on its own. A throw during assignment never changes
|
||||||
|
the initialization state of any optional object involved:
|
||||||
|
</p>
|
||||||
|
<pre class="programlisting"><span class="identifier">optional</span><span class="special"><</span><span class="identifier">T</span><span class="special">></span> <span class="identifier">opt1</span><span class="special">(</span><span class="identifier">val1</span><span class="special">);</span>
|
||||||
|
<span class="identifier">optional</span><span class="special"><</span><span class="identifier">T</span><span class="special">></span> <span class="identifier">opt2</span><span class="special">(</span><span class="identifier">val2</span><span class="special">);</span>
|
||||||
|
<span class="identifier">assert</span><span class="special">(</span><span class="identifier">opt1</span><span class="special">);</span>
|
||||||
|
<span class="identifier">assert</span><span class="special">(</span><span class="identifier">opt2</span><span class="special">);</span>
|
||||||
|
|
||||||
|
<span class="keyword">try</span>
|
||||||
|
<span class="special">{</span>
|
||||||
|
<span class="identifier">opt1</span> <span class="special">=</span> <span class="identifier">opt2</span><span class="special">;</span> <span class="comment">// throws</span>
|
||||||
|
<span class="special">}</span>
|
||||||
|
<span class="keyword">catch</span><span class="special">(...)</span>
|
||||||
|
<span class="special">{</span>
|
||||||
|
<span class="identifier">assert</span><span class="special">(</span><span class="identifier">opt1</span><span class="special">);</span>
|
||||||
|
<span class="identifier">assert</span><span class="special">(</span><span class="identifier">opt2</span><span class="special">);</span>
|
||||||
|
<span class="special">}</span>
|
||||||
|
</pre>
|
||||||
|
<p>
|
||||||
|
This also applies to move assignments/constructors. However, move operations
|
||||||
|
are made no-throw more often.
|
||||||
|
</p>
|
||||||
|
<p>
|
||||||
|
Operation <code class="computeroutput"><span class="identifier">emplace</span></code> provides
|
||||||
|
basic exception safety guarantee. If it throws, the optional object becomes
|
||||||
|
uninitialized regardless of its initial state, and its previous contained
|
||||||
|
value (if any) is destroyed. It doesn't call any assignment or move/copy
|
||||||
|
constructor on <code class="computeroutput"><span class="identifier">T</span></code>.
|
||||||
|
</p>
|
||||||
|
<h5>
|
||||||
|
<a name="boost_optional.tutorial.exception_safety_guarantees.h0"></a>
|
||||||
|
<span class="phrase"><a name="boost_optional.tutorial.exception_safety_guarantees.swap"></a></span><a class="link" href="exception_safety_guarantees.html#boost_optional.tutorial.exception_safety_guarantees.swap">Swap</a>
|
||||||
|
</h5>
|
||||||
|
<p>
|
||||||
|
Unless <code class="computeroutput"><span class="identifier">swap</span></code> on optional is
|
||||||
|
customized, its primary implementation forwards calls to <code class="computeroutput"><span class="identifier">T</span></code>'s
|
||||||
|
<code class="computeroutput"><span class="identifier">swap</span></code> or move constructor
|
||||||
|
(depending on the initialization state of the optional objects). Thus, if
|
||||||
|
both <code class="computeroutput"><span class="identifier">T</span></code>'s <code class="computeroutput"><span class="identifier">swap</span></code>
|
||||||
|
and move constructor never throw, <code class="computeroutput"><span class="identifier">swap</span></code>
|
||||||
|
on <code class="computeroutput"><span class="identifier">optional</span><span class="special"><</span><span class="identifier">T</span><span class="special">></span></code> never
|
||||||
|
throws. similarly, if both <code class="computeroutput"><span class="identifier">T</span></code>'s
|
||||||
|
<code class="computeroutput"><span class="identifier">swap</span></code> and move constructor
|
||||||
|
offer strong guarantee, <code class="computeroutput"><span class="identifier">swap</span></code>
|
||||||
|
on <code class="computeroutput"><span class="identifier">optional</span><span class="special"><</span><span class="identifier">T</span><span class="special">></span></code> also
|
||||||
|
offers a strong guarantee.
|
||||||
|
</p>
|
||||||
|
<p>
|
||||||
|
In case <code class="computeroutput"><span class="identifier">swap</span></code> on optional
|
||||||
|
is customized, the call to <code class="computeroutput"><span class="identifier">T</span></code>'s
|
||||||
|
move constructor are replaced with the calls to <code class="computeroutput"><span class="identifier">T</span></code>'s
|
||||||
|
default constructor followed by <code class="computeroutput"><span class="identifier">swap</span></code>.
|
||||||
|
(This is more useful on older compilers that do not support move semantics,
|
||||||
|
when one wants to acheive stronger exception safety guarantees.) In this
|
||||||
|
case the exception safety guarantees for <code class="computeroutput"><span class="identifier">swap</span></code>
|
||||||
|
are reliant on the guarantees of <code class="computeroutput"><span class="identifier">T</span></code>'s
|
||||||
|
<code class="computeroutput"><span class="identifier">swap</span></code> and default constructor
|
||||||
|
</p>
|
||||||
|
</div>
|
||||||
|
<table xmlns:rev="http://www.cs.rpi.edu/~gregod/boost/tools/doc/revision" width="100%"><tr>
|
||||||
|
<td align="left"></td>
|
||||||
|
<td align="right"><div class="copyright-footer">Copyright © 2003-2007 Fernando Luis Cacciola Carballal<br>Copyright © 2014 Andrzej Krzemieński<p>
|
||||||
|
Distributed under the Boost Software License, Version 1.0. (See accompanying
|
||||||
|
file LICENSE_1_0.txt or copy at <a href="http://www.boost.org/LICENSE_1_0.txt" target="_top">http://www.boost.org/LICENSE_1_0.txt</a>)
|
||||||
|
</p>
|
||||||
|
</div></td>
|
||||||
|
</tr></table>
|
||||||
|
<hr>
|
||||||
|
<div class="spirit-nav">
|
||||||
|
<a accesskey="p" href="a_note_about_optional_bool_.html"><img src="../../../../../../doc/src/images/prev.png" alt="Prev"></a><a accesskey="u" href="../../optional/tutorial.html"><img src="../../../../../../doc/src/images/up.png" alt="Up"></a><a accesskey="h" href="../../index.html"><img src="../../../../../../doc/src/images/home.png" alt="Home"></a><a accesskey="n" href="type_requirements.html"><img src="../../../../../../doc/src/images/next.png" alt="Next"></a>
|
||||||
|
</div>
|
||||||
|
</body>
|
||||||
|
</html>
|
197
doc/html/boost_optional/tutorial/in_place_factories.html
Normal file
197
doc/html/boost_optional/tutorial/in_place_factories.html
Normal file
@ -0,0 +1,197 @@
|
|||||||
|
<html>
|
||||||
|
<head>
|
||||||
|
<meta http-equiv="Content-Type" content="text/html; charset=US-ASCII">
|
||||||
|
<title>In-Place Factories</title>
|
||||||
|
<link rel="stylesheet" href="../../../../../../doc/src/boostbook.css" type="text/css">
|
||||||
|
<meta name="generator" content="DocBook XSL Stylesheets V1.78.1">
|
||||||
|
<link rel="home" href="../../index.html" title="Chapter 1. Boost.Optional">
|
||||||
|
<link rel="up" href="../../optional/tutorial.html" title="Tutorial">
|
||||||
|
<link rel="prev" href="rebinding_semantics_for_assignment_of_optional_references.html" title="Rebinding semantics for assignment of optional references">
|
||||||
|
<link rel="next" href="a_note_about_optional_bool_.html" title="A note about optional<bool>">
|
||||||
|
</head>
|
||||||
|
<body bgcolor="white" text="black" link="#0000FF" vlink="#840084" alink="#0000FF">
|
||||||
|
<table cellpadding="2" width="100%"><tr>
|
||||||
|
<td valign="top"><img alt="Boost C++ Libraries" width="277" height="86" src="../../../../../../boost.png"></td>
|
||||||
|
<td align="center"><a href="../../../../../../index.html">Home</a></td>
|
||||||
|
<td align="center"><a href="../../../../../../libs/libraries.htm">Libraries</a></td>
|
||||||
|
<td align="center"><a href="http://www.boost.org/users/people.html">People</a></td>
|
||||||
|
<td align="center"><a href="http://www.boost.org/users/faq.html">FAQ</a></td>
|
||||||
|
<td align="center"><a href="../../../../../../more/index.htm">More</a></td>
|
||||||
|
</tr></table>
|
||||||
|
<hr>
|
||||||
|
<div class="spirit-nav">
|
||||||
|
<a accesskey="p" href="rebinding_semantics_for_assignment_of_optional_references.html"><img src="../../../../../../doc/src/images/prev.png" alt="Prev"></a><a accesskey="u" href="../../optional/tutorial.html"><img src="../../../../../../doc/src/images/up.png" alt="Up"></a><a accesskey="h" href="../../index.html"><img src="../../../../../../doc/src/images/home.png" alt="Home"></a><a accesskey="n" href="a_note_about_optional_bool_.html"><img src="../../../../../../doc/src/images/next.png" alt="Next"></a>
|
||||||
|
</div>
|
||||||
|
<div class="section">
|
||||||
|
<div class="titlepage"><div><div><h3 class="title">
|
||||||
|
<a name="boost_optional.tutorial.in_place_factories"></a><a class="link" href="in_place_factories.html" title="In-Place Factories">In-Place
|
||||||
|
Factories</a>
|
||||||
|
</h3></div></div></div>
|
||||||
|
<p>
|
||||||
|
One of the typical problems with wrappers and containers is that their interfaces
|
||||||
|
usually provide an operation to initialize or assign the contained object
|
||||||
|
as a copy of some other object. This not only requires the underlying type
|
||||||
|
to be <a href="../../../../../utility/CopyConstructible.html" target="_top">Copy Constructible</a>,
|
||||||
|
but also requires the existence of a fully constructed object, often temporary,
|
||||||
|
just to follow the copy from:
|
||||||
|
</p>
|
||||||
|
<pre class="programlisting"><span class="keyword">struct</span> <span class="identifier">X</span>
|
||||||
|
<span class="special">{</span>
|
||||||
|
<span class="identifier">X</span> <span class="special">(</span> <span class="keyword">int</span><span class="special">,</span> <span class="identifier">std</span><span class="special">::</span><span class="identifier">string</span> <span class="special">)</span> <span class="special">;</span>
|
||||||
|
<span class="special">}</span> <span class="special">;</span>
|
||||||
|
|
||||||
|
<span class="keyword">class</span> <span class="identifier">W</span>
|
||||||
|
<span class="special">{</span>
|
||||||
|
<span class="identifier">X</span> <span class="identifier">wrapped_</span> <span class="special">;</span>
|
||||||
|
|
||||||
|
<span class="keyword">public</span><span class="special">:</span>
|
||||||
|
|
||||||
|
<span class="identifier">W</span> <span class="special">(</span> <span class="identifier">X</span> <span class="keyword">const</span><span class="special">&</span> <span class="identifier">x</span> <span class="special">)</span> <span class="special">:</span> <span class="identifier">wrapped_</span><span class="special">(</span><span class="identifier">x</span><span class="special">)</span> <span class="special">{}</span>
|
||||||
|
<span class="special">}</span> <span class="special">;</span>
|
||||||
|
|
||||||
|
<span class="keyword">void</span> <span class="identifier">foo</span><span class="special">()</span>
|
||||||
|
<span class="special">{</span>
|
||||||
|
<span class="comment">// Temporary object created.</span>
|
||||||
|
<span class="identifier">W</span> <span class="special">(</span> <span class="identifier">X</span><span class="special">(</span><span class="number">123</span><span class="special">,</span><span class="string">"hello"</span><span class="special">)</span> <span class="special">)</span> <span class="special">;</span>
|
||||||
|
<span class="special">}</span>
|
||||||
|
</pre>
|
||||||
|
<p>
|
||||||
|
A solution to this problem is to support direct construction of the contained
|
||||||
|
object right in the container's storage. In this scheme, the user only needs
|
||||||
|
to supply the arguments to the constructor to use in the wrapped object construction.
|
||||||
|
</p>
|
||||||
|
<pre class="programlisting"><span class="keyword">class</span> <span class="identifier">W</span>
|
||||||
|
<span class="special">{</span>
|
||||||
|
<span class="identifier">X</span> <span class="identifier">wrapped_</span> <span class="special">;</span>
|
||||||
|
|
||||||
|
<span class="keyword">public</span><span class="special">:</span>
|
||||||
|
|
||||||
|
<span class="identifier">W</span> <span class="special">(</span> <span class="identifier">X</span> <span class="keyword">const</span><span class="special">&</span> <span class="identifier">x</span> <span class="special">)</span> <span class="special">:</span> <span class="identifier">wrapped_</span><span class="special">(</span><span class="identifier">x</span><span class="special">)</span> <span class="special">{}</span>
|
||||||
|
<span class="identifier">W</span> <span class="special">(</span> <span class="keyword">int</span> <span class="identifier">a0</span><span class="special">,</span> <span class="identifier">std</span><span class="special">::</span><span class="identifier">string</span> <span class="identifier">a1</span><span class="special">)</span> <span class="special">:</span> <span class="identifier">wrapped_</span><span class="special">(</span><span class="identifier">a0</span><span class="special">,</span><span class="identifier">a1</span><span class="special">)</span> <span class="special">{}</span>
|
||||||
|
<span class="special">}</span> <span class="special">;</span>
|
||||||
|
|
||||||
|
<span class="keyword">void</span> <span class="identifier">foo</span><span class="special">()</span>
|
||||||
|
<span class="special">{</span>
|
||||||
|
<span class="comment">// Wrapped object constructed in-place</span>
|
||||||
|
<span class="comment">// No temporary created.</span>
|
||||||
|
<span class="identifier">W</span> <span class="special">(</span><span class="number">123</span><span class="special">,</span><span class="string">"hello"</span><span class="special">)</span> <span class="special">;</span>
|
||||||
|
<span class="special">}</span>
|
||||||
|
</pre>
|
||||||
|
<p>
|
||||||
|
A limitation of this method is that it doesn't scale well to wrapped objects
|
||||||
|
with multiple constructors nor to generic code were the constructor overloads
|
||||||
|
are unknown.
|
||||||
|
</p>
|
||||||
|
<p>
|
||||||
|
The solution presented in this library is the family of <span class="bold"><strong>InPlaceFactories</strong></span>
|
||||||
|
and <span class="bold"><strong>TypedInPlaceFactories</strong></span>. These factories
|
||||||
|
are a family of classes which encapsulate an increasing number of arbitrary
|
||||||
|
constructor parameters and supply a method to construct an object of a given
|
||||||
|
type using those parameters at an address specified by the user via placement
|
||||||
|
new.
|
||||||
|
</p>
|
||||||
|
<p>
|
||||||
|
For example, one member of this family looks like:
|
||||||
|
</p>
|
||||||
|
<pre class="programlisting"><span class="keyword">template</span><span class="special"><</span><span class="keyword">class</span> <span class="identifier">T</span><span class="special">,</span><span class="keyword">class</span> <span class="identifier">A0</span><span class="special">,</span> <span class="keyword">class</span> <span class="identifier">A1</span><span class="special">></span>
|
||||||
|
<span class="keyword">class</span> <span class="identifier">TypedInPlaceFactory2</span>
|
||||||
|
<span class="special">{</span>
|
||||||
|
<span class="identifier">A0</span> <span class="identifier">m_a0</span> <span class="special">;</span> <span class="identifier">A1</span> <span class="identifier">m_a1</span> <span class="special">;</span>
|
||||||
|
|
||||||
|
<span class="keyword">public</span><span class="special">:</span>
|
||||||
|
|
||||||
|
<span class="identifier">TypedInPlaceFactory2</span><span class="special">(</span> <span class="identifier">A0</span> <span class="keyword">const</span><span class="special">&</span> <span class="identifier">a0</span><span class="special">,</span> <span class="identifier">A1</span> <span class="keyword">const</span><span class="special">&</span> <span class="identifier">a1</span> <span class="special">)</span> <span class="special">:</span> <span class="identifier">m_a0</span><span class="special">(</span><span class="identifier">a0</span><span class="special">),</span> <span class="identifier">m_a1</span><span class="special">(</span><span class="identifier">a1</span><span class="special">)</span> <span class="special">{}</span>
|
||||||
|
|
||||||
|
<span class="keyword">void</span> <span class="identifier">construct</span> <span class="special">(</span> <span class="keyword">void</span><span class="special">*</span> <span class="identifier">p</span> <span class="special">)</span> <span class="special">{</span> <span class="keyword">new</span> <span class="special">(</span><span class="identifier">p</span><span class="special">)</span> <span class="identifier">T</span><span class="special">(</span><span class="identifier">m_a0</span><span class="special">,</span><span class="identifier">m_a1</span><span class="special">)</span> <span class="special">;</span> <span class="special">}</span>
|
||||||
|
<span class="special">}</span> <span class="special">;</span>
|
||||||
|
</pre>
|
||||||
|
<p>
|
||||||
|
A wrapper class aware of this can use it as:
|
||||||
|
</p>
|
||||||
|
<pre class="programlisting"><span class="keyword">class</span> <span class="identifier">W</span>
|
||||||
|
<span class="special">{</span>
|
||||||
|
<span class="identifier">X</span> <span class="identifier">wrapped_</span> <span class="special">;</span>
|
||||||
|
|
||||||
|
<span class="keyword">public</span><span class="special">:</span>
|
||||||
|
|
||||||
|
<span class="identifier">W</span> <span class="special">(</span> <span class="identifier">X</span> <span class="keyword">const</span><span class="special">&</span> <span class="identifier">x</span> <span class="special">)</span> <span class="special">:</span> <span class="identifier">wrapped_</span><span class="special">(</span><span class="identifier">x</span><span class="special">)</span> <span class="special">{}</span>
|
||||||
|
<span class="identifier">W</span> <span class="special">(</span> <span class="identifier">TypedInPlaceFactory2</span> <span class="keyword">const</span><span class="special">&</span> <span class="identifier">fac</span> <span class="special">)</span> <span class="special">{</span> <span class="identifier">fac</span><span class="special">.</span><span class="identifier">construct</span><span class="special">(&</span><span class="identifier">wrapped_</span><span class="special">)</span> <span class="special">;</span> <span class="special">}</span>
|
||||||
|
<span class="special">}</span> <span class="special">;</span>
|
||||||
|
|
||||||
|
<span class="keyword">void</span> <span class="identifier">foo</span><span class="special">()</span>
|
||||||
|
<span class="special">{</span>
|
||||||
|
<span class="comment">// Wrapped object constructed in-place via a TypedInPlaceFactory.</span>
|
||||||
|
<span class="comment">// No temporary created.</span>
|
||||||
|
<span class="identifier">W</span> <span class="special">(</span> <span class="identifier">TypedInPlaceFactory2</span><span class="special"><</span><span class="identifier">X</span><span class="special">,</span><span class="keyword">int</span><span class="special">,</span><span class="identifier">std</span><span class="special">::</span><span class="identifier">string</span><span class="special">>(</span><span class="number">123</span><span class="special">,</span><span class="string">"hello"</span><span class="special">))</span> <span class="special">;</span>
|
||||||
|
<span class="special">}</span>
|
||||||
|
</pre>
|
||||||
|
<p>
|
||||||
|
The factories are divided in two groups:
|
||||||
|
</p>
|
||||||
|
<div class="itemizedlist"><ul class="itemizedlist" style="list-style-type: disc; ">
|
||||||
|
<li class="listitem">
|
||||||
|
<span class="underline">TypedInPlaceFactories</span>: those which
|
||||||
|
take the target type as a primary template parameter.
|
||||||
|
</li>
|
||||||
|
<li class="listitem">
|
||||||
|
<span class="underline">InPlaceFactories</span>: those with a
|
||||||
|
template <code class="computeroutput"><span class="identifier">construct</span><span class="special">(</span><span class="keyword">void</span><span class="special">*)</span></code>
|
||||||
|
member function taking the target type.
|
||||||
|
</li>
|
||||||
|
</ul></div>
|
||||||
|
<p>
|
||||||
|
Within each group, all the family members differ only in the number of parameters
|
||||||
|
allowed.
|
||||||
|
</p>
|
||||||
|
<p>
|
||||||
|
This library provides an overloaded set of helper template functions to construct
|
||||||
|
these factories without requiring unnecessary template parameters:
|
||||||
|
</p>
|
||||||
|
<pre class="programlisting"><span class="keyword">template</span><span class="special"><</span><span class="keyword">class</span> <span class="identifier">A0</span><span class="special">,...,</span><span class="keyword">class</span> <span class="identifier">AN</span><span class="special">></span>
|
||||||
|
<span class="identifier">InPlaceFactoryN</span> <span class="special"><</span><span class="identifier">A0</span><span class="special">,...,</span><span class="identifier">AN</span><span class="special">></span> <span class="identifier">in_place</span> <span class="special">(</span> <span class="identifier">A0</span> <span class="keyword">const</span><span class="special">&</span> <span class="identifier">a0</span><span class="special">,</span> <span class="special">...,</span> <span class="identifier">AN</span> <span class="keyword">const</span><span class="special">&</span> <span class="identifier">aN</span><span class="special">)</span> <span class="special">;</span>
|
||||||
|
|
||||||
|
<span class="keyword">template</span><span class="special"><</span><span class="keyword">class</span> <span class="identifier">T</span><span class="special">,</span><span class="keyword">class</span> <span class="identifier">A0</span><span class="special">,...,</span><span class="keyword">class</span> <span class="identifier">AN</span><span class="special">></span>
|
||||||
|
<span class="identifier">TypedInPlaceFactoryN</span> <span class="special"><</span><span class="identifier">T</span><span class="special">,</span><span class="identifier">A0</span><span class="special">,...,</span><span class="identifier">AN</span><span class="special">></span> <span class="identifier">in_place</span> <span class="special">(</span> <span class="identifier">T</span> <span class="keyword">const</span><span class="special">&</span> <span class="identifier">a0</span><span class="special">,</span> <span class="identifier">A0</span> <span class="keyword">const</span><span class="special">&</span> <span class="identifier">a0</span><span class="special">,</span> <span class="special">...,</span> <span class="identifier">AN</span> <span class="keyword">const</span><span class="special">&</span> <span class="identifier">aN</span><span class="special">)</span> <span class="special">;</span>
|
||||||
|
</pre>
|
||||||
|
<p>
|
||||||
|
In-place factories can be used generically by the wrapper and user as follows:
|
||||||
|
</p>
|
||||||
|
<pre class="programlisting"><span class="keyword">class</span> <span class="identifier">W</span>
|
||||||
|
<span class="special">{</span>
|
||||||
|
<span class="identifier">X</span> <span class="identifier">wrapped_</span> <span class="special">;</span>
|
||||||
|
|
||||||
|
<span class="keyword">public</span><span class="special">:</span>
|
||||||
|
|
||||||
|
<span class="identifier">W</span> <span class="special">(</span> <span class="identifier">X</span> <span class="keyword">const</span><span class="special">&</span> <span class="identifier">x</span> <span class="special">)</span> <span class="special">:</span> <span class="identifier">wrapped_</span><span class="special">(</span><span class="identifier">x</span><span class="special">)</span> <span class="special">{}</span>
|
||||||
|
|
||||||
|
<span class="keyword">template</span><span class="special"><</span> <span class="keyword">class</span> <span class="identifier">InPlaceFactory</span> <span class="special">></span>
|
||||||
|
<span class="identifier">W</span> <span class="special">(</span> <span class="identifier">InPlaceFactory</span> <span class="keyword">const</span><span class="special">&</span> <span class="identifier">fac</span> <span class="special">)</span> <span class="special">{</span> <span class="identifier">fac</span><span class="special">.</span><span class="keyword">template</span> <span class="special"><</span><span class="identifier">X</span><span class="special">></span><span class="identifier">construct</span><span class="special">(&</span><span class="identifier">wrapped_</span><span class="special">)</span> <span class="special">;</span> <span class="special">}</span>
|
||||||
|
|
||||||
|
<span class="special">}</span> <span class="special">;</span>
|
||||||
|
|
||||||
|
<span class="keyword">void</span> <span class="identifier">foo</span><span class="special">()</span>
|
||||||
|
<span class="special">{</span>
|
||||||
|
<span class="comment">// Wrapped object constructed in-place via a InPlaceFactory.</span>
|
||||||
|
<span class="comment">// No temporary created.</span>
|
||||||
|
<span class="identifier">W</span> <span class="special">(</span> <span class="identifier">in_place</span><span class="special">(</span><span class="number">123</span><span class="special">,</span><span class="string">"hello"</span><span class="special">)</span> <span class="special">)</span> <span class="special">;</span>
|
||||||
|
<span class="special">}</span>
|
||||||
|
</pre>
|
||||||
|
<p>
|
||||||
|
The factories are implemented in the headers: <a href="../../../../../../boost/utility/in_place_factory.hpp" target="_top">in_place_factory.hpp</a>
|
||||||
|
and <a href="../../../../../../boost/utility/typed_in_place_factory.hpp" target="_top">typed_in_place_factory.hpp</a>
|
||||||
|
</p>
|
||||||
|
</div>
|
||||||
|
<table xmlns:rev="http://www.cs.rpi.edu/~gregod/boost/tools/doc/revision" width="100%"><tr>
|
||||||
|
<td align="left"></td>
|
||||||
|
<td align="right"><div class="copyright-footer">Copyright © 2003-2007 Fernando Luis Cacciola Carballal<br>Copyright © 2014 Andrzej Krzemieński<p>
|
||||||
|
Distributed under the Boost Software License, Version 1.0. (See accompanying
|
||||||
|
file LICENSE_1_0.txt or copy at <a href="http://www.boost.org/LICENSE_1_0.txt" target="_top">http://www.boost.org/LICENSE_1_0.txt</a>)
|
||||||
|
</p>
|
||||||
|
</div></td>
|
||||||
|
</tr></table>
|
||||||
|
<hr>
|
||||||
|
<div class="spirit-nav">
|
||||||
|
<a accesskey="p" href="rebinding_semantics_for_assignment_of_optional_references.html"><img src="../../../../../../doc/src/images/prev.png" alt="Prev"></a><a accesskey="u" href="../../optional/tutorial.html"><img src="../../../../../../doc/src/images/up.png" alt="Up"></a><a accesskey="h" href="../../index.html"><img src="../../../../../../doc/src/images/home.png" alt="Home"></a><a accesskey="n" href="a_note_about_optional_bool_.html"><img src="../../../../../../doc/src/images/next.png" alt="Next"></a>
|
||||||
|
</div>
|
||||||
|
</body>
|
||||||
|
</html>
|
129
doc/html/boost_optional/tutorial/motivation.html
Normal file
129
doc/html/boost_optional/tutorial/motivation.html
Normal file
@ -0,0 +1,129 @@
|
|||||||
|
<html>
|
||||||
|
<head>
|
||||||
|
<meta http-equiv="Content-Type" content="text/html; charset=US-ASCII">
|
||||||
|
<title>Motivation</title>
|
||||||
|
<link rel="stylesheet" href="../../../../../../doc/src/boostbook.css" type="text/css">
|
||||||
|
<meta name="generator" content="DocBook XSL Stylesheets V1.78.1">
|
||||||
|
<link rel="home" href="../../index.html" title="Chapter 1. Boost.Optional">
|
||||||
|
<link rel="up" href="../../optional/tutorial.html" title="Tutorial">
|
||||||
|
<link rel="prev" href="../../optional/tutorial.html" title="Tutorial">
|
||||||
|
<link rel="next" href="design_overview.html" title="Design Overview">
|
||||||
|
</head>
|
||||||
|
<body bgcolor="white" text="black" link="#0000FF" vlink="#840084" alink="#0000FF">
|
||||||
|
<table cellpadding="2" width="100%"><tr>
|
||||||
|
<td valign="top"><img alt="Boost C++ Libraries" width="277" height="86" src="../../../../../../boost.png"></td>
|
||||||
|
<td align="center"><a href="../../../../../../index.html">Home</a></td>
|
||||||
|
<td align="center"><a href="../../../../../../libs/libraries.htm">Libraries</a></td>
|
||||||
|
<td align="center"><a href="http://www.boost.org/users/people.html">People</a></td>
|
||||||
|
<td align="center"><a href="http://www.boost.org/users/faq.html">FAQ</a></td>
|
||||||
|
<td align="center"><a href="../../../../../../more/index.htm">More</a></td>
|
||||||
|
</tr></table>
|
||||||
|
<hr>
|
||||||
|
<div class="spirit-nav">
|
||||||
|
<a accesskey="p" href="../../optional/tutorial.html"><img src="../../../../../../doc/src/images/prev.png" alt="Prev"></a><a accesskey="u" href="../../optional/tutorial.html"><img src="../../../../../../doc/src/images/up.png" alt="Up"></a><a accesskey="h" href="../../index.html"><img src="../../../../../../doc/src/images/home.png" alt="Home"></a><a accesskey="n" href="design_overview.html"><img src="../../../../../../doc/src/images/next.png" alt="Next"></a>
|
||||||
|
</div>
|
||||||
|
<div class="section">
|
||||||
|
<div class="titlepage"><div><div><h3 class="title">
|
||||||
|
<a name="boost_optional.tutorial.motivation"></a><a class="link" href="motivation.html" title="Motivation">Motivation</a>
|
||||||
|
</h3></div></div></div>
|
||||||
|
<p>
|
||||||
|
Consider these functions which should return a value but which might not
|
||||||
|
have a value to return:
|
||||||
|
</p>
|
||||||
|
<div class="itemizedlist"><ul class="itemizedlist" style="list-style-type: disc; ">
|
||||||
|
<li class="listitem">
|
||||||
|
(A) <code class="computeroutput"><span class="keyword">double</span> <span class="identifier">sqrt</span><span class="special">(</span><span class="keyword">double</span> <span class="identifier">n</span> <span class="special">);</span></code>
|
||||||
|
</li>
|
||||||
|
<li class="listitem">
|
||||||
|
(B) <code class="computeroutput"><span class="keyword">char</span> <span class="identifier">get_async_input</span><span class="special">();</span></code>
|
||||||
|
</li>
|
||||||
|
<li class="listitem">
|
||||||
|
(C) <code class="computeroutput"><span class="identifier">point</span> <span class="identifier">polygon</span><span class="special">::</span><span class="identifier">get_any_point_effectively_inside</span><span class="special">();</span></code>
|
||||||
|
</li>
|
||||||
|
</ul></div>
|
||||||
|
<p>
|
||||||
|
There are different approaches to the issue of not having a value to return.
|
||||||
|
</p>
|
||||||
|
<p>
|
||||||
|
A typical approach is to consider the existence of a valid return value as
|
||||||
|
a postcondition, so that if the function cannot compute the value to return,
|
||||||
|
it has either undefined behavior (and can use assert in a debug build) or
|
||||||
|
uses a runtime check and throws an exception if the postcondition is violated.
|
||||||
|
This is a reasonable choice for example, for function (A), because the lack
|
||||||
|
of a proper return value is directly related to an invalid parameter (out
|
||||||
|
of domain argument), so it is appropriate to require the callee to supply
|
||||||
|
only parameters in a valid domain for execution to continue normally.
|
||||||
|
</p>
|
||||||
|
<p>
|
||||||
|
However, function (B), because of its asynchronous nature, does not fail
|
||||||
|
just because it can't find a value to return; so it is incorrect to consider
|
||||||
|
such a situation an error and assert or throw an exception. This function
|
||||||
|
must return, and somehow, must tell the callee that it is not returning a
|
||||||
|
meaningful value.
|
||||||
|
</p>
|
||||||
|
<p>
|
||||||
|
A similar situation occurs with function (C): it is conceptually an error
|
||||||
|
to ask a <span class="emphasis"><em>null-area</em></span> polygon to return a point inside
|
||||||
|
itself, but in many applications, it is just impractical for performance
|
||||||
|
reasons to treat this as an error (because detecting that the polygon has
|
||||||
|
no area might be too expensive to be required to be tested previously), and
|
||||||
|
either an arbitrary point (typically at infinity) is returned, or some efficient
|
||||||
|
way to tell the callee that there is no such point is used.
|
||||||
|
</p>
|
||||||
|
<p>
|
||||||
|
There are various mechanisms to let functions communicate that the returned
|
||||||
|
value is not valid. One such mechanism, which is quite common since it has
|
||||||
|
zero or negligible overhead, is to use a special value which is reserved
|
||||||
|
to communicate this. Classical examples of such special values are <code class="computeroutput"><span class="identifier">EOF</span></code>, <code class="computeroutput"><span class="identifier">string</span><span class="special">::</span><span class="identifier">npos</span></code>,
|
||||||
|
points at infinity, etc...
|
||||||
|
</p>
|
||||||
|
<p>
|
||||||
|
When those values exist, i.e. the return type can hold all meaningful values
|
||||||
|
<span class="emphasis"><em>plus</em></span> the <span class="emphasis"><em>signal</em></span> value, this mechanism
|
||||||
|
is quite appropriate and well known. Unfortunately, there are cases when
|
||||||
|
such values do not exist. In these cases, the usual alternative is either
|
||||||
|
to use a wider type, such as <code class="computeroutput"><span class="keyword">int</span></code>
|
||||||
|
in place of <code class="computeroutput"><span class="keyword">char</span></code>; or a compound
|
||||||
|
type, such as <code class="computeroutput"><span class="identifier">std</span><span class="special">::</span><span class="identifier">pair</span><span class="special"><</span><span class="identifier">point</span><span class="special">,</span><span class="keyword">bool</span><span class="special">></span></code>.
|
||||||
|
</p>
|
||||||
|
<p>
|
||||||
|
Returning a <code class="computeroutput"><span class="identifier">std</span><span class="special">::</span><span class="identifier">pair</span><span class="special"><</span><span class="identifier">T</span><span class="special">,</span><span class="keyword">bool</span><span class="special">></span></code>, thus attaching a boolean flag to the
|
||||||
|
result which indicates if the result is meaningful, has the advantage that
|
||||||
|
can be turned into a consistent idiom since the first element of the pair
|
||||||
|
can be whatever the function would conceptually return. For example, the
|
||||||
|
last two functions could have the following interface:
|
||||||
|
</p>
|
||||||
|
<pre class="programlisting"><span class="identifier">std</span><span class="special">::</span><span class="identifier">pair</span><span class="special"><</span><span class="keyword">char</span><span class="special">,</span><span class="keyword">bool</span><span class="special">></span> <span class="identifier">get_async_input</span><span class="special">();</span>
|
||||||
|
<span class="identifier">std</span><span class="special">::</span><span class="identifier">pair</span><span class="special"><</span><span class="identifier">point</span><span class="special">,</span><span class="keyword">bool</span><span class="special">></span> <span class="identifier">polygon</span><span class="special">::</span><span class="identifier">get_any_point_effectively_inside</span><span class="special">();</span>
|
||||||
|
</pre>
|
||||||
|
<p>
|
||||||
|
These functions use a consistent interface for dealing with possibly nonexistent
|
||||||
|
results:
|
||||||
|
</p>
|
||||||
|
<pre class="programlisting"><span class="identifier">std</span><span class="special">::</span><span class="identifier">pair</span><span class="special"><</span><span class="identifier">point</span><span class="special">,</span><span class="keyword">bool</span><span class="special">></span> <span class="identifier">p</span> <span class="special">=</span> <span class="identifier">poly</span><span class="special">.</span><span class="identifier">get_any_point_effectively_inside</span><span class="special">();</span>
|
||||||
|
<span class="keyword">if</span> <span class="special">(</span> <span class="identifier">p</span><span class="special">.</span><span class="identifier">second</span> <span class="special">)</span>
|
||||||
|
<span class="identifier">flood_fill</span><span class="special">(</span><span class="identifier">p</span><span class="special">.</span><span class="identifier">first</span><span class="special">);</span>
|
||||||
|
</pre>
|
||||||
|
<p>
|
||||||
|
However, not only is this quite a burden syntactically, it is also error
|
||||||
|
prone since the user can easily use the function result (first element of
|
||||||
|
the pair) without ever checking if it has a valid value.
|
||||||
|
</p>
|
||||||
|
<p>
|
||||||
|
Clearly, we need a better idiom.
|
||||||
|
</p>
|
||||||
|
</div>
|
||||||
|
<table xmlns:rev="http://www.cs.rpi.edu/~gregod/boost/tools/doc/revision" width="100%"><tr>
|
||||||
|
<td align="left"></td>
|
||||||
|
<td align="right"><div class="copyright-footer">Copyright © 2003-2007 Fernando Luis Cacciola Carballal<br>Copyright © 2014 Andrzej Krzemieński<p>
|
||||||
|
Distributed under the Boost Software License, Version 1.0. (See accompanying
|
||||||
|
file LICENSE_1_0.txt or copy at <a href="http://www.boost.org/LICENSE_1_0.txt" target="_top">http://www.boost.org/LICENSE_1_0.txt</a>)
|
||||||
|
</p>
|
||||||
|
</div></td>
|
||||||
|
</tr></table>
|
||||||
|
<hr>
|
||||||
|
<div class="spirit-nav">
|
||||||
|
<a accesskey="p" href="../../optional/tutorial.html"><img src="../../../../../../doc/src/images/prev.png" alt="Prev"></a><a accesskey="u" href="../../optional/tutorial.html"><img src="../../../../../../doc/src/images/up.png" alt="Up"></a><a accesskey="h" href="../../index.html"><img src="../../../../../../doc/src/images/home.png" alt="Home"></a><a accesskey="n" href="design_overview.html"><img src="../../../../../../doc/src/images/next.png" alt="Next"></a>
|
||||||
|
</div>
|
||||||
|
</body>
|
||||||
|
</html>
|
115
doc/html/boost_optional/tutorial/optional_references.html
Normal file
115
doc/html/boost_optional/tutorial/optional_references.html
Normal file
@ -0,0 +1,115 @@
|
|||||||
|
<html>
|
||||||
|
<head>
|
||||||
|
<meta http-equiv="Content-Type" content="text/html; charset=US-ASCII">
|
||||||
|
<title>Optional references</title>
|
||||||
|
<link rel="stylesheet" href="../../../../../../doc/src/boostbook.css" type="text/css">
|
||||||
|
<meta name="generator" content="DocBook XSL Stylesheets V1.78.1">
|
||||||
|
<link rel="home" href="../../index.html" title="Chapter 1. Boost.Optional">
|
||||||
|
<link rel="up" href="../../optional/tutorial.html" title="Tutorial">
|
||||||
|
<link rel="prev" href="design_overview.html" title="Design Overview">
|
||||||
|
<link rel="next" href="rebinding_semantics_for_assignment_of_optional_references.html" title="Rebinding semantics for assignment of optional references">
|
||||||
|
</head>
|
||||||
|
<body bgcolor="white" text="black" link="#0000FF" vlink="#840084" alink="#0000FF">
|
||||||
|
<table cellpadding="2" width="100%"><tr>
|
||||||
|
<td valign="top"><img alt="Boost C++ Libraries" width="277" height="86" src="../../../../../../boost.png"></td>
|
||||||
|
<td align="center"><a href="../../../../../../index.html">Home</a></td>
|
||||||
|
<td align="center"><a href="../../../../../../libs/libraries.htm">Libraries</a></td>
|
||||||
|
<td align="center"><a href="http://www.boost.org/users/people.html">People</a></td>
|
||||||
|
<td align="center"><a href="http://www.boost.org/users/faq.html">FAQ</a></td>
|
||||||
|
<td align="center"><a href="../../../../../../more/index.htm">More</a></td>
|
||||||
|
</tr></table>
|
||||||
|
<hr>
|
||||||
|
<div class="spirit-nav">
|
||||||
|
<a accesskey="p" href="design_overview.html"><img src="../../../../../../doc/src/images/prev.png" alt="Prev"></a><a accesskey="u" href="../../optional/tutorial.html"><img src="../../../../../../doc/src/images/up.png" alt="Up"></a><a accesskey="h" href="../../index.html"><img src="../../../../../../doc/src/images/home.png" alt="Home"></a><a accesskey="n" href="rebinding_semantics_for_assignment_of_optional_references.html"><img src="../../../../../../doc/src/images/next.png" alt="Next"></a>
|
||||||
|
</div>
|
||||||
|
<div class="section">
|
||||||
|
<div class="titlepage"><div><div><h3 class="title">
|
||||||
|
<a name="boost_optional.tutorial.optional_references"></a><a class="link" href="optional_references.html" title="Optional references">Optional
|
||||||
|
references</a>
|
||||||
|
</h3></div></div></div>
|
||||||
|
<p>
|
||||||
|
This library allows the template parameter <code class="computeroutput"><span class="identifier">T</span></code>
|
||||||
|
to be of reference type: <code class="computeroutput"><span class="identifier">T</span><span class="special">&</span></code>, and to some extent, <code class="computeroutput"><span class="identifier">T</span>
|
||||||
|
<span class="keyword">const</span><span class="special">&</span></code>.
|
||||||
|
</p>
|
||||||
|
<p>
|
||||||
|
However, since references are not real objects some restrictions apply and
|
||||||
|
some operations are not available in this case:
|
||||||
|
</p>
|
||||||
|
<div class="itemizedlist"><ul class="itemizedlist" style="list-style-type: disc; ">
|
||||||
|
<li class="listitem">
|
||||||
|
Converting constructors
|
||||||
|
</li>
|
||||||
|
<li class="listitem">
|
||||||
|
Converting assignment
|
||||||
|
</li>
|
||||||
|
<li class="listitem">
|
||||||
|
InPlace construction
|
||||||
|
</li>
|
||||||
|
<li class="listitem">
|
||||||
|
InPlace assignment
|
||||||
|
</li>
|
||||||
|
<li class="listitem">
|
||||||
|
Value-access via pointer
|
||||||
|
</li>
|
||||||
|
</ul></div>
|
||||||
|
<p>
|
||||||
|
Also, even though <code class="computeroutput"><span class="identifier">optional</span><span class="special"><</span><span class="identifier">T</span><span class="special">&></span></code>
|
||||||
|
treats it wrapped pseudo-object much as a real value, a true real reference
|
||||||
|
is stored so aliasing will ocurr:
|
||||||
|
</p>
|
||||||
|
<div class="itemizedlist"><ul class="itemizedlist" style="list-style-type: disc; ">
|
||||||
|
<li class="listitem">
|
||||||
|
Copies of <code class="computeroutput"><span class="identifier">optional</span><span class="special"><</span><span class="identifier">T</span><span class="special">&></span></code>
|
||||||
|
will copy the references but all these references will nonetheless refer
|
||||||
|
to the same object.
|
||||||
|
</li>
|
||||||
|
<li class="listitem">
|
||||||
|
Value-access will actually provide access to the referenced object rather
|
||||||
|
than the reference itself.
|
||||||
|
</li>
|
||||||
|
</ul></div>
|
||||||
|
<div class="warning"><table border="0" summary="Warning">
|
||||||
|
<tr>
|
||||||
|
<td rowspan="2" align="center" valign="top" width="25"><img alt="[Warning]" src="../../../../../../doc/src/images/warning.png"></td>
|
||||||
|
<th align="left">Warning</th>
|
||||||
|
</tr>
|
||||||
|
<tr><td align="left" valign="top"><p>
|
||||||
|
On compilers that do not conform to Standard C++ rules of reference binding,
|
||||||
|
operations on optional references might give adverse results: rather than
|
||||||
|
binding a reference to a designated object they may create an unexpected
|
||||||
|
temporary and bind to it. For more details see <a class="link" href="../dependencies_and_portability/optional_reference_binding.html" title="Optional Reference Binding">Dependencies
|
||||||
|
and Portability section</a>.
|
||||||
|
</p></td></tr>
|
||||||
|
</table></div>
|
||||||
|
<h5>
|
||||||
|
<a name="boost_optional.tutorial.optional_references.h0"></a>
|
||||||
|
<span class="phrase"><a name="boost_optional.tutorial.optional_references.rvalue_references"></a></span><a class="link" href="optional_references.html#boost_optional.tutorial.optional_references.rvalue_references">Rvalue
|
||||||
|
references</a>
|
||||||
|
</h5>
|
||||||
|
<p>
|
||||||
|
Rvalue references and lvalue references to const have the ability in C++
|
||||||
|
to extend the life time of a temporary they bind to. Optional references
|
||||||
|
do not have this capability, therefore to avoid surprising effects it is
|
||||||
|
not possible to initialize an optional references from a temporary. Optional
|
||||||
|
rvalue references are disabled altogether. Also, the initialization and assignment
|
||||||
|
of an optional reference to const from rvalue reference is disabled.
|
||||||
|
</p>
|
||||||
|
<pre class="programlisting"><span class="keyword">const</span> <span class="keyword">int</span><span class="special">&</span> <span class="identifier">i</span> <span class="special">=</span> <span class="number">1</span><span class="special">;</span> <span class="comment">// legal</span>
|
||||||
|
<span class="identifier">optional</span><span class="special"><</span><span class="keyword">const</span> <span class="keyword">int</span><span class="special">&></span> <span class="identifier">oi</span> <span class="special">=</span> <span class="number">1</span><span class="special">;</span> <span class="comment">// illegal</span>
|
||||||
|
</pre>
|
||||||
|
</div>
|
||||||
|
<table xmlns:rev="http://www.cs.rpi.edu/~gregod/boost/tools/doc/revision" width="100%"><tr>
|
||||||
|
<td align="left"></td>
|
||||||
|
<td align="right"><div class="copyright-footer">Copyright © 2003-2007 Fernando Luis Cacciola Carballal<br>Copyright © 2014 Andrzej Krzemieński<p>
|
||||||
|
Distributed under the Boost Software License, Version 1.0. (See accompanying
|
||||||
|
file LICENSE_1_0.txt or copy at <a href="http://www.boost.org/LICENSE_1_0.txt" target="_top">http://www.boost.org/LICENSE_1_0.txt</a>)
|
||||||
|
</p>
|
||||||
|
</div></td>
|
||||||
|
</tr></table>
|
||||||
|
<hr>
|
||||||
|
<div class="spirit-nav">
|
||||||
|
<a accesskey="p" href="design_overview.html"><img src="../../../../../../doc/src/images/prev.png" alt="Prev"></a><a accesskey="u" href="../../optional/tutorial.html"><img src="../../../../../../doc/src/images/up.png" alt="Up"></a><a accesskey="h" href="../../index.html"><img src="../../../../../../doc/src/images/home.png" alt="Home"></a><a accesskey="n" href="rebinding_semantics_for_assignment_of_optional_references.html"><img src="../../../../../../doc/src/images/next.png" alt="Next"></a>
|
||||||
|
</div>
|
||||||
|
</body>
|
||||||
|
</html>
|
@ -0,0 +1,149 @@
|
|||||||
|
<html>
|
||||||
|
<head>
|
||||||
|
<meta http-equiv="Content-Type" content="text/html; charset=US-ASCII">
|
||||||
|
<title>Rebinding semantics for assignment of optional references</title>
|
||||||
|
<link rel="stylesheet" href="../../../../../../doc/src/boostbook.css" type="text/css">
|
||||||
|
<meta name="generator" content="DocBook XSL Stylesheets V1.78.1">
|
||||||
|
<link rel="home" href="../../index.html" title="Chapter 1. Boost.Optional">
|
||||||
|
<link rel="up" href="../../optional/tutorial.html" title="Tutorial">
|
||||||
|
<link rel="prev" href="optional_references.html" title="Optional references">
|
||||||
|
<link rel="next" href="in_place_factories.html" title="In-Place Factories">
|
||||||
|
</head>
|
||||||
|
<body bgcolor="white" text="black" link="#0000FF" vlink="#840084" alink="#0000FF">
|
||||||
|
<table cellpadding="2" width="100%"><tr>
|
||||||
|
<td valign="top"><img alt="Boost C++ Libraries" width="277" height="86" src="../../../../../../boost.png"></td>
|
||||||
|
<td align="center"><a href="../../../../../../index.html">Home</a></td>
|
||||||
|
<td align="center"><a href="../../../../../../libs/libraries.htm">Libraries</a></td>
|
||||||
|
<td align="center"><a href="http://www.boost.org/users/people.html">People</a></td>
|
||||||
|
<td align="center"><a href="http://www.boost.org/users/faq.html">FAQ</a></td>
|
||||||
|
<td align="center"><a href="../../../../../../more/index.htm">More</a></td>
|
||||||
|
</tr></table>
|
||||||
|
<hr>
|
||||||
|
<div class="spirit-nav">
|
||||||
|
<a accesskey="p" href="optional_references.html"><img src="../../../../../../doc/src/images/prev.png" alt="Prev"></a><a accesskey="u" href="../../optional/tutorial.html"><img src="../../../../../../doc/src/images/up.png" alt="Up"></a><a accesskey="h" href="../../index.html"><img src="../../../../../../doc/src/images/home.png" alt="Home"></a><a accesskey="n" href="in_place_factories.html"><img src="../../../../../../doc/src/images/next.png" alt="Next"></a>
|
||||||
|
</div>
|
||||||
|
<div class="section">
|
||||||
|
<div class="titlepage"><div><div><h3 class="title">
|
||||||
|
<a name="boost_optional.tutorial.rebinding_semantics_for_assignment_of_optional_references"></a><a class="link" href="rebinding_semantics_for_assignment_of_optional_references.html" title="Rebinding semantics for assignment of optional references">Rebinding
|
||||||
|
semantics for assignment of optional references</a>
|
||||||
|
</h3></div></div></div>
|
||||||
|
<p>
|
||||||
|
If you assign to an <span class="emphasis"><em>uninitialized </em></span> <code class="computeroutput"><span class="identifier">optional</span><span class="special"><</span><span class="identifier">T</span><span class="special">&></span></code>
|
||||||
|
the effect is to bind (for the first time) to the object. Clearly, there
|
||||||
|
is no other choice.
|
||||||
|
</p>
|
||||||
|
<pre class="programlisting"><span class="keyword">int</span> <span class="identifier">x</span> <span class="special">=</span> <span class="number">1</span> <span class="special">;</span>
|
||||||
|
<span class="keyword">int</span><span class="special">&</span> <span class="identifier">rx</span> <span class="special">=</span> <span class="identifier">x</span> <span class="special">;</span>
|
||||||
|
<span class="identifier">optional</span><span class="special"><</span><span class="keyword">int</span><span class="special">&></span> <span class="identifier">ora</span> <span class="special">;</span>
|
||||||
|
<span class="identifier">optional</span><span class="special"><</span><span class="keyword">int</span><span class="special">&></span> <span class="identifier">orb</span><span class="special">(</span><span class="identifier">x</span><span class="special">)</span> <span class="special">;</span>
|
||||||
|
<span class="identifier">ora</span> <span class="special">=</span> <span class="identifier">orb</span> <span class="special">;</span> <span class="comment">// now 'ora' is bound to 'x' through 'rx'</span>
|
||||||
|
<span class="special">*</span><span class="identifier">ora</span> <span class="special">=</span> <span class="number">2</span> <span class="special">;</span> <span class="comment">// Changes value of 'x' through 'ora'</span>
|
||||||
|
<span class="identifier">assert</span><span class="special">(</span><span class="identifier">x</span><span class="special">==</span><span class="number">2</span><span class="special">);</span>
|
||||||
|
</pre>
|
||||||
|
<p>
|
||||||
|
If you assign to a bare C++ reference, the assignment is forwarded to the
|
||||||
|
referenced object; its value changes but the reference is never rebound.
|
||||||
|
</p>
|
||||||
|
<pre class="programlisting"><span class="keyword">int</span> <span class="identifier">a</span> <span class="special">=</span> <span class="number">1</span> <span class="special">;</span>
|
||||||
|
<span class="keyword">int</span><span class="special">&</span> <span class="identifier">ra</span> <span class="special">=</span> <span class="identifier">a</span> <span class="special">;</span>
|
||||||
|
<span class="keyword">int</span> <span class="identifier">b</span> <span class="special">=</span> <span class="number">2</span> <span class="special">;</span>
|
||||||
|
<span class="keyword">int</span><span class="special">&</span> <span class="identifier">rb</span> <span class="special">=</span> <span class="identifier">b</span> <span class="special">;</span>
|
||||||
|
<span class="identifier">ra</span> <span class="special">=</span> <span class="identifier">rb</span> <span class="special">;</span> <span class="comment">// Changes the value of 'a' to 'b'</span>
|
||||||
|
<span class="identifier">assert</span><span class="special">(</span><span class="identifier">a</span><span class="special">==</span><span class="identifier">b</span><span class="special">);</span>
|
||||||
|
<span class="identifier">b</span> <span class="special">=</span> <span class="number">3</span> <span class="special">;</span>
|
||||||
|
<span class="identifier">assert</span><span class="special">(</span><span class="identifier">ra</span><span class="special">!=</span><span class="identifier">b</span><span class="special">);</span> <span class="comment">// 'ra' is not rebound to 'b'</span>
|
||||||
|
</pre>
|
||||||
|
<p>
|
||||||
|
Now, if you assign to an <span class="emphasis"><em>initialized </em></span> <code class="computeroutput"><span class="identifier">optional</span><span class="special"><</span><span class="identifier">T</span><span class="special">&></span></code>,
|
||||||
|
the effect is to <span class="bold"><strong>rebind</strong></span> to the new object
|
||||||
|
instead of assigning the referee. This is unlike bare C++ references.
|
||||||
|
</p>
|
||||||
|
<pre class="programlisting"><span class="keyword">int</span> <span class="identifier">a</span> <span class="special">=</span> <span class="number">1</span> <span class="special">;</span>
|
||||||
|
<span class="keyword">int</span> <span class="identifier">b</span> <span class="special">=</span> <span class="number">2</span> <span class="special">;</span>
|
||||||
|
<span class="keyword">int</span><span class="special">&</span> <span class="identifier">ra</span> <span class="special">=</span> <span class="identifier">a</span> <span class="special">;</span>
|
||||||
|
<span class="keyword">int</span><span class="special">&</span> <span class="identifier">rb</span> <span class="special">=</span> <span class="identifier">b</span> <span class="special">;</span>
|
||||||
|
<span class="identifier">optional</span><span class="special"><</span><span class="keyword">int</span><span class="special">&></span> <span class="identifier">ora</span><span class="special">(</span><span class="identifier">ra</span><span class="special">)</span> <span class="special">;</span>
|
||||||
|
<span class="identifier">optional</span><span class="special"><</span><span class="keyword">int</span><span class="special">&></span> <span class="identifier">orb</span><span class="special">(</span><span class="identifier">rb</span><span class="special">)</span> <span class="special">;</span>
|
||||||
|
<span class="identifier">ora</span> <span class="special">=</span> <span class="identifier">orb</span> <span class="special">;</span> <span class="comment">// 'ora' is rebound to 'b'</span>
|
||||||
|
<span class="special">*</span><span class="identifier">ora</span> <span class="special">=</span> <span class="number">3</span> <span class="special">;</span> <span class="comment">// Changes value of 'b' (not 'a')</span>
|
||||||
|
<span class="identifier">assert</span><span class="special">(</span><span class="identifier">a</span><span class="special">==</span><span class="number">1</span><span class="special">);</span>
|
||||||
|
<span class="identifier">assert</span><span class="special">(</span><span class="identifier">b</span><span class="special">==</span><span class="number">3</span><span class="special">);</span>
|
||||||
|
</pre>
|
||||||
|
<h5>
|
||||||
|
<a name="boost_optional.tutorial.rebinding_semantics_for_assignment_of_optional_references.h0"></a>
|
||||||
|
<span class="phrase"><a name="boost_optional.tutorial.rebinding_semantics_for_assignment_of_optional_references.rationale"></a></span><a class="link" href="rebinding_semantics_for_assignment_of_optional_references.html#boost_optional.tutorial.rebinding_semantics_for_assignment_of_optional_references.rationale">Rationale</a>
|
||||||
|
</h5>
|
||||||
|
<p>
|
||||||
|
Rebinding semantics for the assignment of <span class="emphasis"><em>initialized </em></span>
|
||||||
|
<code class="computeroutput"><span class="identifier">optional</span></code> references has been
|
||||||
|
chosen to provide <span class="bold"><strong>consistency among initialization
|
||||||
|
states</strong></span> even at the expense of lack of consistency with the semantics
|
||||||
|
of bare C++ references. It is true that <code class="computeroutput"><span class="identifier">optional</span><span class="special"><</span><span class="identifier">U</span><span class="special">></span></code>
|
||||||
|
strives to behave as much as possible as <code class="computeroutput"><span class="identifier">U</span></code>
|
||||||
|
does whenever it is initialized; but in the case when <code class="computeroutput"><span class="identifier">U</span></code>
|
||||||
|
is <code class="computeroutput"><span class="identifier">T</span><span class="special">&</span></code>,
|
||||||
|
doing so would result in inconsistent behavior w.r.t to the lvalue initialization
|
||||||
|
state.
|
||||||
|
</p>
|
||||||
|
<p>
|
||||||
|
Imagine <code class="computeroutput"><span class="identifier">optional</span><span class="special"><</span><span class="identifier">T</span><span class="special">&></span></code>
|
||||||
|
forwarding assignment to the referenced object (thus changing the referenced
|
||||||
|
object value but not rebinding), and consider the following code:
|
||||||
|
</p>
|
||||||
|
<pre class="programlisting"><span class="identifier">optional</span><span class="special"><</span><span class="keyword">int</span><span class="special">&></span> <span class="identifier">a</span> <span class="special">=</span> <span class="identifier">get</span><span class="special">();</span>
|
||||||
|
<span class="keyword">int</span> <span class="identifier">x</span> <span class="special">=</span> <span class="number">1</span> <span class="special">;</span>
|
||||||
|
<span class="keyword">int</span><span class="special">&</span> <span class="identifier">rx</span> <span class="special">=</span> <span class="identifier">x</span> <span class="special">;</span>
|
||||||
|
<span class="identifier">optional</span><span class="special"><</span><span class="keyword">int</span><span class="special">&></span> <span class="identifier">b</span><span class="special">(</span><span class="identifier">rx</span><span class="special">);</span>
|
||||||
|
<span class="identifier">a</span> <span class="special">=</span> <span class="identifier">b</span> <span class="special">;</span>
|
||||||
|
</pre>
|
||||||
|
<p>
|
||||||
|
What does the assignment do?
|
||||||
|
</p>
|
||||||
|
<p>
|
||||||
|
If <code class="computeroutput"><span class="identifier">a</span></code> is <span class="emphasis"><em>uninitialized</em></span>,
|
||||||
|
the answer is clear: it binds to <code class="computeroutput"><span class="identifier">x</span></code>
|
||||||
|
(we now have another reference to <code class="computeroutput"><span class="identifier">x</span></code>).
|
||||||
|
But what if <code class="computeroutput"><span class="identifier">a</span></code> is already
|
||||||
|
<span class="emphasis"><em>initialized</em></span>? it would change the value of the referenced
|
||||||
|
object (whatever that is); which is inconsistent with the other possible
|
||||||
|
case.
|
||||||
|
</p>
|
||||||
|
<p>
|
||||||
|
If <code class="computeroutput"><span class="identifier">optional</span><span class="special"><</span><span class="identifier">T</span><span class="special">&></span></code>
|
||||||
|
would assign just like <code class="computeroutput"><span class="identifier">T</span><span class="special">&</span></code> does, you would never be able to use
|
||||||
|
Optional's assignment without explicitly handling the previous initialization
|
||||||
|
state unless your code is capable of functioning whether after the assignment,
|
||||||
|
<code class="computeroutput"><span class="identifier">a</span></code> aliases the same object
|
||||||
|
as <code class="computeroutput"><span class="identifier">b</span></code> or not.
|
||||||
|
</p>
|
||||||
|
<p>
|
||||||
|
That is, you would have to discriminate in order to be consistent.
|
||||||
|
</p>
|
||||||
|
<p>
|
||||||
|
If in your code rebinding to another object is not an option, then it is
|
||||||
|
very likely that binding for the first time isn't either. In such case, assignment
|
||||||
|
to an <span class="emphasis"><em>uninitialized </em></span> <code class="computeroutput"><span class="identifier">optional</span><span class="special"><</span><span class="identifier">T</span><span class="special">&></span></code>
|
||||||
|
shall be prohibited. It is quite possible that in such a scenario it is a
|
||||||
|
precondition that the lvalue must be already initialized. If it isn't, then
|
||||||
|
binding for the first time is OK while rebinding is not which is IMO very
|
||||||
|
unlikely. In such a scenario, you can assign the value itself directly, as
|
||||||
|
in:
|
||||||
|
</p>
|
||||||
|
<pre class="programlisting"><span class="identifier">assert</span><span class="special">(!!</span><span class="identifier">opt</span><span class="special">);</span>
|
||||||
|
<span class="special">*</span><span class="identifier">opt</span><span class="special">=</span><span class="identifier">value</span><span class="special">;</span>
|
||||||
|
</pre>
|
||||||
|
</div>
|
||||||
|
<table xmlns:rev="http://www.cs.rpi.edu/~gregod/boost/tools/doc/revision" width="100%"><tr>
|
||||||
|
<td align="left"></td>
|
||||||
|
<td align="right"><div class="copyright-footer">Copyright © 2003-2007 Fernando Luis Cacciola Carballal<br>Copyright © 2014 Andrzej Krzemieński<p>
|
||||||
|
Distributed under the Boost Software License, Version 1.0. (See accompanying
|
||||||
|
file LICENSE_1_0.txt or copy at <a href="http://www.boost.org/LICENSE_1_0.txt" target="_top">http://www.boost.org/LICENSE_1_0.txt</a>)
|
||||||
|
</p>
|
||||||
|
</div></td>
|
||||||
|
</tr></table>
|
||||||
|
<hr>
|
||||||
|
<div class="spirit-nav">
|
||||||
|
<a accesskey="p" href="optional_references.html"><img src="../../../../../../doc/src/images/prev.png" alt="Prev"></a><a accesskey="u" href="../../optional/tutorial.html"><img src="../../../../../../doc/src/images/up.png" alt="Up"></a><a accesskey="h" href="../../index.html"><img src="../../../../../../doc/src/images/home.png" alt="Home"></a><a accesskey="n" href="in_place_factories.html"><img src="../../../../../../doc/src/images/next.png" alt="Next"></a>
|
||||||
|
</div>
|
||||||
|
</body>
|
||||||
|
</html>
|
61
doc/html/boost_optional/tutorial/type_requirements.html
Normal file
61
doc/html/boost_optional/tutorial/type_requirements.html
Normal file
@ -0,0 +1,61 @@
|
|||||||
|
<html>
|
||||||
|
<head>
|
||||||
|
<meta http-equiv="Content-Type" content="text/html; charset=US-ASCII">
|
||||||
|
<title>Type requirements</title>
|
||||||
|
<link rel="stylesheet" href="../../../../../../doc/src/boostbook.css" type="text/css">
|
||||||
|
<meta name="generator" content="DocBook XSL Stylesheets V1.78.1">
|
||||||
|
<link rel="home" href="../../index.html" title="Chapter 1. Boost.Optional">
|
||||||
|
<link rel="up" href="../../optional/tutorial.html" title="Tutorial">
|
||||||
|
<link rel="prev" href="exception_safety_guarantees.html" title="Exception Safety Guarantees">
|
||||||
|
<link rel="next" href="../../optional/reference.html" title="Reference">
|
||||||
|
</head>
|
||||||
|
<body bgcolor="white" text="black" link="#0000FF" vlink="#840084" alink="#0000FF">
|
||||||
|
<table cellpadding="2" width="100%"><tr>
|
||||||
|
<td valign="top"><img alt="Boost C++ Libraries" width="277" height="86" src="../../../../../../boost.png"></td>
|
||||||
|
<td align="center"><a href="../../../../../../index.html">Home</a></td>
|
||||||
|
<td align="center"><a href="../../../../../../libs/libraries.htm">Libraries</a></td>
|
||||||
|
<td align="center"><a href="http://www.boost.org/users/people.html">People</a></td>
|
||||||
|
<td align="center"><a href="http://www.boost.org/users/faq.html">FAQ</a></td>
|
||||||
|
<td align="center"><a href="../../../../../../more/index.htm">More</a></td>
|
||||||
|
</tr></table>
|
||||||
|
<hr>
|
||||||
|
<div class="spirit-nav">
|
||||||
|
<a accesskey="p" href="exception_safety_guarantees.html"><img src="../../../../../../doc/src/images/prev.png" alt="Prev"></a><a accesskey="u" href="../../optional/tutorial.html"><img src="../../../../../../doc/src/images/up.png" alt="Up"></a><a accesskey="h" href="../../index.html"><img src="../../../../../../doc/src/images/home.png" alt="Home"></a><a accesskey="n" href="../../optional/reference.html"><img src="../../../../../../doc/src/images/next.png" alt="Next"></a>
|
||||||
|
</div>
|
||||||
|
<div class="section">
|
||||||
|
<div class="titlepage"><div><div><h3 class="title">
|
||||||
|
<a name="boost_optional.tutorial.type_requirements"></a><a class="link" href="type_requirements.html" title="Type requirements">Type requirements</a>
|
||||||
|
</h3></div></div></div>
|
||||||
|
<p>
|
||||||
|
At the very minimum for <code class="computeroutput"><span class="identifier">optional</span><span class="special"><</span><span class="identifier">T</span><span class="special">></span></code>
|
||||||
|
to work with a minimum interface it is required that <code class="computeroutput"><span class="identifier">T</span></code>
|
||||||
|
has a publicly accessible no-throw destructor. In that case you need to initialize
|
||||||
|
the optional object with function <code class="computeroutput"><span class="identifier">emplace</span><span class="special">()</span></code> or use <span class="bold"><strong>InPlaceFactories</strong></span>.
|
||||||
|
Additionally, if <code class="computeroutput"><span class="identifier">T</span></code> is <code class="computeroutput"><span class="identifier">Moveable</span></code>, <code class="computeroutput"><span class="identifier">optional</span><span class="special"><</span><span class="identifier">T</span><span class="special">></span></code>
|
||||||
|
is also <code class="computeroutput"><span class="identifier">Moveable</span></code> and can
|
||||||
|
be easily initialized from an rvalue of type <code class="computeroutput"><span class="identifier">T</span></code>
|
||||||
|
and be passed by value. Additionally, if <code class="computeroutput"><span class="identifier">T</span></code>
|
||||||
|
is <code class="computeroutput"><span class="identifier">Copyable</span></code>, <code class="computeroutput"><span class="identifier">optional</span><span class="special"><</span><span class="identifier">T</span><span class="special">></span></code> is
|
||||||
|
also <code class="computeroutput"><span class="identifier">Copyable</span></code> and can be
|
||||||
|
easily initialized from an lvalue of type <code class="computeroutput"><span class="identifier">T</span></code>.
|
||||||
|
</p>
|
||||||
|
<p>
|
||||||
|
<code class="computeroutput"><span class="identifier">T</span></code> <span class="underline">is
|
||||||
|
not</span> required to be <a href="http://www.sgi.com/tech/stl/DefaultConstructible.html" target="_top">Default
|
||||||
|
Constructible</a>.
|
||||||
|
</p>
|
||||||
|
</div>
|
||||||
|
<table xmlns:rev="http://www.cs.rpi.edu/~gregod/boost/tools/doc/revision" width="100%"><tr>
|
||||||
|
<td align="left"></td>
|
||||||
|
<td align="right"><div class="copyright-footer">Copyright © 2003-2007 Fernando Luis Cacciola Carballal<br>Copyright © 2014 Andrzej Krzemieński<p>
|
||||||
|
Distributed under the Boost Software License, Version 1.0. (See accompanying
|
||||||
|
file LICENSE_1_0.txt or copy at <a href="http://www.boost.org/LICENSE_1_0.txt" target="_top">http://www.boost.org/LICENSE_1_0.txt</a>)
|
||||||
|
</p>
|
||||||
|
</div></td>
|
||||||
|
</tr></table>
|
||||||
|
<hr>
|
||||||
|
<div class="spirit-nav">
|
||||||
|
<a accesskey="p" href="exception_safety_guarantees.html"><img src="../../../../../../doc/src/images/prev.png" alt="Prev"></a><a accesskey="u" href="../../optional/tutorial.html"><img src="../../../../../../doc/src/images/up.png" alt="Up"></a><a accesskey="h" href="../../index.html"><img src="../../../../../../doc/src/images/home.png" alt="Home"></a><a accesskey="n" href="../../optional/reference.html"><img src="../../../../../../doc/src/images/next.png" alt="Next"></a>
|
||||||
|
</div>
|
||||||
|
</body>
|
||||||
|
</html>
|
@ -34,7 +34,7 @@
|
|||||||
Additionally, if <code class="computeroutput"><span class="identifier">T</span></code> is <code class="computeroutput"><span class="identifier">Moveable</span></code>, <code class="computeroutput"><span class="identifier">optional</span><span class="special"><</span><span class="identifier">T</span><span class="special">></span></code>
|
Additionally, if <code class="computeroutput"><span class="identifier">T</span></code> is <code class="computeroutput"><span class="identifier">Moveable</span></code>, <code class="computeroutput"><span class="identifier">optional</span><span class="special"><</span><span class="identifier">T</span><span class="special">></span></code>
|
||||||
is also <code class="computeroutput"><span class="identifier">Moveable</span></code> and can be
|
is also <code class="computeroutput"><span class="identifier">Moveable</span></code> and can be
|
||||||
easily initialized from an rvalue of type <code class="computeroutput"><span class="identifier">T</span></code>
|
easily initialized from an rvalue of type <code class="computeroutput"><span class="identifier">T</span></code>
|
||||||
and be passed by value. Additionally if <code class="computeroutput"><span class="identifier">T</span></code>
|
and be passed by value. Additionally, if <code class="computeroutput"><span class="identifier">T</span></code>
|
||||||
is <code class="computeroutput"><span class="identifier">Copyable</span></code>, <code class="computeroutput"><span class="identifier">optional</span><span class="special"><</span><span class="identifier">T</span><span class="special">></span></code> is
|
is <code class="computeroutput"><span class="identifier">Copyable</span></code>, <code class="computeroutput"><span class="identifier">optional</span><span class="special"><</span><span class="identifier">T</span><span class="special">></span></code> is
|
||||||
also <code class="computeroutput"><span class="identifier">Copyable</span></code> and can be easily
|
also <code class="computeroutput"><span class="identifier">Copyable</span></code> and can be easily
|
||||||
initialized from an lvalue of type <code class="computeroutput"><span class="identifier">T</span></code>.
|
initialized from an lvalue of type <code class="computeroutput"><span class="identifier">T</span></code>.
|
||||||
|
@ -5,7 +5,7 @@
|
|||||||
<link rel="stylesheet" href="../../../../doc/src/boostbook.css" type="text/css">
|
<link rel="stylesheet" href="../../../../doc/src/boostbook.css" type="text/css">
|
||||||
<meta name="generator" content="DocBook XSL Stylesheets V1.78.1">
|
<meta name="generator" content="DocBook XSL Stylesheets V1.78.1">
|
||||||
<link rel="home" href="index.html" title="Chapter 1. Boost.Optional">
|
<link rel="home" href="index.html" title="Chapter 1. Boost.Optional">
|
||||||
<link rel="next" href="boost_optional/tutorial.html" title="Tutorial">
|
<link rel="next" href="boost_optional/quick_start.html" title="Quick Start">
|
||||||
</head>
|
</head>
|
||||||
<body bgcolor="white" text="black" link="#0000FF" vlink="#840084" alink="#0000FF">
|
<body bgcolor="white" text="black" link="#0000FF" vlink="#840084" alink="#0000FF">
|
||||||
<table cellpadding="2" width="100%"><tr>
|
<table cellpadding="2" width="100%"><tr>
|
||||||
@ -17,7 +17,7 @@
|
|||||||
<td align="center"><a href="../../../../more/index.htm">More</a></td>
|
<td align="center"><a href="../../../../more/index.htm">More</a></td>
|
||||||
</tr></table>
|
</tr></table>
|
||||||
<hr>
|
<hr>
|
||||||
<div class="spirit-nav"><a accesskey="n" href="boost_optional/tutorial.html"><img src="../../../../doc/src/images/next.png" alt="Next"></a></div>
|
<div class="spirit-nav"><a accesskey="n" href="boost_optional/quick_start.html"><img src="../../../../doc/src/images/next.png" alt="Next"></a></div>
|
||||||
<div class="chapter">
|
<div class="chapter">
|
||||||
<div class="titlepage"><div>
|
<div class="titlepage"><div>
|
||||||
<div><h2 class="title">
|
<div><h2 class="title">
|
||||||
@ -37,94 +37,67 @@
|
|||||||
<div class="toc">
|
<div class="toc">
|
||||||
<p><b>Table of Contents</b></p>
|
<p><b>Table of Contents</b></p>
|
||||||
<dl class="toc">
|
<dl class="toc">
|
||||||
<dt><span class="section"><a href="index.html#optional.introduction">Introduction</a></span></dt>
|
<dt><span class="section"><a href="boost_optional/quick_start.html">Quick Start</a></span></dt>
|
||||||
|
<dt><span class="section"><a href="optional/tutorial.html">Tutorial</a></span></dt>
|
||||||
<dd><dl>
|
<dd><dl>
|
||||||
<dt><span class="section"><a href="index.html#optional.introduction.problem">Problem</a></span></dt>
|
<dt><span class="section"><a href="boost_optional/tutorial/motivation.html">Motivation</a></span></dt>
|
||||||
<dt><span class="section"><a href="index.html#optional.introduction.solution">Solution</a></span></dt>
|
<dt><span class="section"><a href="boost_optional/tutorial/design_overview.html">Design Overview</a></span></dt>
|
||||||
|
<dt><span class="section"><a href="boost_optional/tutorial/optional_references.html">Optional
|
||||||
|
references</a></span></dt>
|
||||||
|
<dt><span class="section"><a href="boost_optional/tutorial/rebinding_semantics_for_assignment_of_optional_references.html">Rebinding
|
||||||
|
semantics for assignment of optional references</a></span></dt>
|
||||||
|
<dt><span class="section"><a href="boost_optional/tutorial/in_place_factories.html">In-Place
|
||||||
|
Factories</a></span></dt>
|
||||||
|
<dt><span class="section"><a href="boost_optional/tutorial/a_note_about_optional_bool_.html">A
|
||||||
|
note about optional<bool></a></span></dt>
|
||||||
|
<dt><span class="section"><a href="boost_optional/tutorial/exception_safety_guarantees.html">Exception
|
||||||
|
Safety Guarantees</a></span></dt>
|
||||||
|
<dt><span class="section"><a href="boost_optional/tutorial/type_requirements.html">Type requirements</a></span></dt>
|
||||||
</dl></dd>
|
</dl></dd>
|
||||||
<dt><span class="section"><a href="boost_optional/tutorial.html">Tutorial</a></span></dt>
|
<dt><span class="section"><a href="optional/reference.html">Reference</a></span></dt>
|
||||||
<dd><dl>
|
<dd><dl>
|
||||||
<dt><span class="section"><a href="boost_optional/tutorial.html#boost_optional.tutorial.optional_return_values">Optional
|
<dt><span class="section"><a href="boost_optional/reference/synopsis.html">Synopsis</a></span></dt>
|
||||||
return values</a></span></dt>
|
<dt><span class="section"><a href="boost_optional/reference/detailed_semantics.html">Detailed
|
||||||
<dt><span class="section"><a href="boost_optional/tutorial.html#boost_optional.tutorial.optional_data_members">Optional
|
Semantics</a></span></dt>
|
||||||
data members</a></span></dt>
|
|
||||||
<dt><span class="section"><a href="boost_optional/tutorial.html#boost_optional.tutorial.bypassing_unnecessary_default_construction">Bypassing
|
|
||||||
unnecessary default construction</a></span></dt>
|
|
||||||
</dl></dd>
|
</dl></dd>
|
||||||
<dt><span class="section"><a href="boost_optional/discussion.html">Discussion</a></span></dt>
|
|
||||||
<dt><span class="section"><a href="boost_optional/development.html">Development</a></span></dt>
|
|
||||||
<dd><dl>
|
|
||||||
<dt><span class="section"><a href="boost_optional/development.html#boost_optional.development.the_models">The models</a></span></dt>
|
|
||||||
<dt><span class="section"><a href="boost_optional/development.html#boost_optional.development.the_semantics">The semantics</a></span></dt>
|
|
||||||
<dt><span class="section"><a href="boost_optional/development.html#boost_optional.development.the_interface">The Interface</a></span></dt>
|
|
||||||
</dl></dd>
|
|
||||||
<dt><span class="section"><a href="boost_optional/synopsis.html">Synopsis</a></span></dt>
|
|
||||||
<dt><span class="section"><a href="boost_optional/detailed_semantics.html">Detailed Semantics</a></span></dt>
|
|
||||||
<dt><span class="section"><a href="boost_optional/examples.html">Examples</a></span></dt>
|
|
||||||
<dd><dl>
|
|
||||||
<dt><span class="section"><a href="boost_optional/examples.html#boost_optional.examples.optional_return_values">Optional
|
|
||||||
return values</a></span></dt>
|
|
||||||
<dt><span class="section"><a href="boost_optional/examples.html#boost_optional.examples.optional_local_variables">Optional
|
|
||||||
local variables</a></span></dt>
|
|
||||||
<dt><span class="section"><a href="boost_optional/examples.html#boost_optional.examples.optional_data_members">Optional
|
|
||||||
data members</a></span></dt>
|
|
||||||
<dt><span class="section"><a href="boost_optional/examples.html#boost_optional.examples.bypassing_expensive_unnecessary_default_construction">Bypassing
|
|
||||||
expensive unnecessary default construction</a></span></dt>
|
|
||||||
</dl></dd>
|
|
||||||
<dt><span class="section"><a href="boost_optional/optional_references.html">Optional references</a></span></dt>
|
|
||||||
<dt><span class="section"><a href="boost_optional/rebinding_semantics_for_assignment_of_optional_references.html">Rebinding
|
|
||||||
semantics for assignment of optional references</a></span></dt>
|
|
||||||
<dt><span class="section"><a href="boost_optional/in_place_factories.html">In-Place Factories</a></span></dt>
|
|
||||||
<dt><span class="section"><a href="boost_optional/a_note_about_optional_bool_.html">A note about
|
|
||||||
optional<bool></a></span></dt>
|
|
||||||
<dt><span class="section"><a href="boost_optional/exception_safety_guarantees.html">Exception Safety
|
|
||||||
Guarantees</a></span></dt>
|
|
||||||
<dt><span class="section"><a href="boost_optional/type_requirements.html">Type requirements</a></span></dt>
|
|
||||||
<dt><span class="section"><a href="boost_optional/dependencies_and_portability.html">Dependencies
|
<dt><span class="section"><a href="boost_optional/dependencies_and_portability.html">Dependencies
|
||||||
and Portability</a></span></dt>
|
and Portability</a></span></dt>
|
||||||
<dd><dl><dt><span class="section"><a href="boost_optional/dependencies_and_portability.html#boost_optional.dependencies_and_portability.optional_reference_binding">Optional
|
<dd><dl><dt><span class="section"><a href="boost_optional/dependencies_and_portability/optional_reference_binding.html">Optional
|
||||||
Reference Binding</a></span></dt></dl></dd>
|
Reference Binding</a></span></dt></dl></dd>
|
||||||
<dt><span class="section"><a href="boost_optional/acknowledgments.html">Acknowledgments</a></span></dt>
|
<dt><span class="section"><a href="boost_optional/acknowledgments.html">Acknowledgments</a></span></dt>
|
||||||
</dl>
|
</dl>
|
||||||
</div>
|
</div>
|
||||||
<div class="section">
|
<h3>
|
||||||
<div class="titlepage"><div><div><h2 class="title" style="clear: both">
|
<a name="optional.h0"></a>
|
||||||
<a name="optional.introduction"></a><a class="link" href="index.html#optional.introduction" title="Introduction">Introduction</a>
|
<span class="phrase"><a name="optional.introduction"></a></span><a class="link" href="index.html#optional.introduction">Introduction</a>
|
||||||
</h2></div></div></div>
|
</h3>
|
||||||
<div class="toc"><dl class="toc">
|
|
||||||
<dt><span class="section"><a href="index.html#optional.introduction.problem">Problem</a></span></dt>
|
|
||||||
<dt><span class="section"><a href="index.html#optional.introduction.solution">Solution</a></span></dt>
|
|
||||||
</dl></div>
|
|
||||||
<p>
|
<p>
|
||||||
Class template <code class="computeroutput"><span class="identifier">optional</span></code> is
|
Class template <code class="computeroutput"><span class="identifier">optional</span></code> is a
|
||||||
a wrapper for representing 'optional' (or 'nullable') objects who may not (yet)
|
wrapper for representing 'optional' (or 'nullable') objects who may not (yet)
|
||||||
contain a valid value. Optional objects offer full value semantics; they are
|
contain a valid value. Optional objects offer full value semantics; they are
|
||||||
good for passing by value and usage inside STL containers. This is a header-only
|
good for passing by value and usage inside STL containers. This is a header-only
|
||||||
library.
|
library.
|
||||||
</p>
|
</p>
|
||||||
<div class="section">
|
<h3>
|
||||||
<div class="titlepage"><div><div><h3 class="title">
|
<a name="optional.h1"></a>
|
||||||
<a name="optional.introduction.problem"></a><a class="link" href="index.html#optional.introduction.problem" title="Problem">Problem</a>
|
<span class="phrase"><a name="optional.problem"></a></span><a class="link" href="index.html#optional.problem">Problem</a>
|
||||||
</h3></div></div></div>
|
</h3>
|
||||||
<p>
|
<p>
|
||||||
Suppose we want to read a parameter form a config file which represents some
|
Suppose we want to read a parameter form a config file which represents some
|
||||||
integral value, let's call it <code class="computeroutput"><span class="string">"MaxValue"</span></code>.
|
integral value, let's call it <code class="computeroutput"><span class="string">"MaxValue"</span></code>.
|
||||||
It is possible that this parameter is not specified; such situation is no
|
It is possible that this parameter is not specified; such situation is no error.
|
||||||
error. It is valid to not specify the parameter and in that case the program
|
It is valid to not specify the parameter and in that case the program is supposed
|
||||||
is supposed to behave slightly different. Also suppose that any possible
|
to behave slightly different. Also suppose that any possible value of type <code class="computeroutput"><span class="keyword">int</span></code> is a valid value for <code class="computeroutput"><span class="string">"MaxValue"</span></code>,
|
||||||
value of type <code class="computeroutput"><span class="keyword">int</span></code> is a valid
|
so we cannot jut use <code class="computeroutput"><span class="special">-</span><span class="number">1</span></code>
|
||||||
value for <code class="computeroutput"><span class="string">"MaxValue"</span></code>,
|
to represent the absence of the parameter in the config file.
|
||||||
so we cannot jut use <code class="computeroutput"><span class="special">-</span><span class="number">1</span></code>
|
</p>
|
||||||
to represent the absence of the parameter in the config file.
|
<h3>
|
||||||
</p>
|
<a name="optional.h2"></a>
|
||||||
</div>
|
<span class="phrase"><a name="optional.solution"></a></span><a class="link" href="index.html#optional.solution">Solution</a>
|
||||||
<div class="section">
|
</h3>
|
||||||
<div class="titlepage"><div><div><h3 class="title">
|
|
||||||
<a name="optional.introduction.solution"></a><a class="link" href="index.html#optional.introduction.solution" title="Solution">Solution</a>
|
|
||||||
</h3></div></div></div>
|
|
||||||
<p>
|
<p>
|
||||||
This is how you solve it with <code class="computeroutput"><span class="identifier">boost</span><span class="special">::</span><span class="identifier">optional</span></code>:
|
This is how you solve it with <code class="computeroutput"><span class="identifier">boost</span><span class="special">::</span><span class="identifier">optional</span></code>:
|
||||||
</p>
|
</p>
|
||||||
<pre class="programlisting"><span class="preprocessor">#include</span> <span class="special"><</span><span class="identifier">boost</span><span class="special">/</span><span class="identifier">optional</span><span class="special">.</span><span class="identifier">hpp</span><span class="special">></span>
|
<pre class="programlisting"><span class="preprocessor">#include</span> <span class="special"><</span><span class="identifier">boost</span><span class="special">/</span><span class="identifier">optional</span><span class="special">.</span><span class="identifier">hpp</span><span class="special">></span>
|
||||||
|
|
||||||
<span class="identifier">boost</span><span class="special">::</span><span class="identifier">optional</span><span class="special"><</span><span class="keyword">int</span><span class="special">></span> <span class="identifier">getConfigParam</span><span class="special">(</span><span class="identifier">std</span><span class="special">::</span><span class="identifier">string</span> <span class="identifier">name</span><span class="special">);</span> <span class="comment">// return either an int or a `not-an-int`</span>
|
<span class="identifier">boost</span><span class="special">::</span><span class="identifier">optional</span><span class="special"><</span><span class="keyword">int</span><span class="special">></span> <span class="identifier">getConfigParam</span><span class="special">(</span><span class="identifier">std</span><span class="special">::</span><span class="identifier">string</span> <span class="identifier">name</span><span class="special">);</span> <span class="comment">// return either an int or a `not-an-int`</span>
|
||||||
@ -138,13 +111,11 @@
|
|||||||
<span class="special">}</span>
|
<span class="special">}</span>
|
||||||
</pre>
|
</pre>
|
||||||
</div>
|
</div>
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
<table xmlns:rev="http://www.cs.rpi.edu/~gregod/boost/tools/doc/revision" width="100%"><tr>
|
<table xmlns:rev="http://www.cs.rpi.edu/~gregod/boost/tools/doc/revision" width="100%"><tr>
|
||||||
<td align="left"><p><small>Last revised: June 03, 2014 at 14:35:30 GMT</small></p></td>
|
<td align="left"><p><small>Last revised: June 04, 2014 at 16:06:37 GMT</small></p></td>
|
||||||
<td align="right"><div class="copyright-footer"></div></td>
|
<td align="right"><div class="copyright-footer"></div></td>
|
||||||
</tr></table>
|
</tr></table>
|
||||||
<hr>
|
<hr>
|
||||||
<div class="spirit-nav"><a accesskey="n" href="boost_optional/tutorial.html"><img src="../../../../doc/src/images/next.png" alt="Next"></a></div>
|
<div class="spirit-nav"><a accesskey="n" href="boost_optional/quick_start.html"><img src="../../../../doc/src/images/next.png" alt="Next"></a></div>
|
||||||
</body>
|
</body>
|
||||||
</html>
|
</html>
|
||||||
|
82
doc/html/optional/introduction.html
Normal file
82
doc/html/optional/introduction.html
Normal file
@ -0,0 +1,82 @@
|
|||||||
|
<html>
|
||||||
|
<head>
|
||||||
|
<meta http-equiv="Content-Type" content="text/html; charset=US-ASCII">
|
||||||
|
<title>Introduction</title>
|
||||||
|
<link rel="stylesheet" href="../../../../../doc/src/boostbook.css" type="text/css">
|
||||||
|
<meta name="generator" content="DocBook XSL Stylesheets V1.78.1">
|
||||||
|
<link rel="home" href="../index.html" title="Chapter 1. Boost.Optional">
|
||||||
|
<link rel="up" href="../index.html" title="Chapter 1. Boost.Optional">
|
||||||
|
<link rel="prev" href="../index.html" title="Chapter 1. Boost.Optional">
|
||||||
|
<link rel="next" href="../boost_optional/quick_start.html" title="Quick Start">
|
||||||
|
</head>
|
||||||
|
<body bgcolor="white" text="black" link="#0000FF" vlink="#840084" alink="#0000FF">
|
||||||
|
<table cellpadding="2" width="100%"><tr>
|
||||||
|
<td valign="top"><img alt="Boost C++ Libraries" width="277" height="86" src="../../../../../boost.png"></td>
|
||||||
|
<td align="center"><a href="../../../../../index.html">Home</a></td>
|
||||||
|
<td align="center"><a href="../../../../../libs/libraries.htm">Libraries</a></td>
|
||||||
|
<td align="center"><a href="http://www.boost.org/users/people.html">People</a></td>
|
||||||
|
<td align="center"><a href="http://www.boost.org/users/faq.html">FAQ</a></td>
|
||||||
|
<td align="center"><a href="../../../../../more/index.htm">More</a></td>
|
||||||
|
</tr></table>
|
||||||
|
<hr>
|
||||||
|
<div class="spirit-nav">
|
||||||
|
<a accesskey="p" href="../index.html"><img src="../../../../../doc/src/images/prev.png" alt="Prev"></a><a accesskey="u" href="../index.html"><img src="../../../../../doc/src/images/up.png" alt="Up"></a><a accesskey="h" href="../index.html"><img src="../../../../../doc/src/images/home.png" alt="Home"></a><a accesskey="n" href="../boost_optional/quick_start.html"><img src="../../../../../doc/src/images/next.png" alt="Next"></a>
|
||||||
|
</div>
|
||||||
|
<div class="section">
|
||||||
|
<div class="titlepage"><div><div><h2 class="title" style="clear: both">
|
||||||
|
<a name="optional.introduction"></a><a class="link" href="introduction.html" title="Introduction">Introduction</a>
|
||||||
|
</h2></div></div></div>
|
||||||
|
<p>
|
||||||
|
Class template <code class="computeroutput"><span class="identifier">optional</span></code> is
|
||||||
|
a wrapper for representing 'optional' (or 'nullable') objects who may not (yet)
|
||||||
|
contain a valid value. Optional objects offer full value semantics; they are
|
||||||
|
good for passing by value and usage inside STL containers. This is a header-only
|
||||||
|
library.
|
||||||
|
</p>
|
||||||
|
<h4>
|
||||||
|
<a name="optional.introduction.h0"></a>
|
||||||
|
<span class="phrase"><a name="optional.introduction.problem"></a></span><a class="link" href="introduction.html#optional.introduction.problem">Problem</a>
|
||||||
|
</h4>
|
||||||
|
<p>
|
||||||
|
Suppose we want to read a parameter form a config file which represents some
|
||||||
|
integral value, let's call it <code class="computeroutput"><span class="string">"MaxValue"</span></code>.
|
||||||
|
It is possible that this parameter is not specified; such situation is no error.
|
||||||
|
It is valid to not specify the parameter and in that case the program is supposed
|
||||||
|
to behave slightly different. Also suppose that any possible value of type
|
||||||
|
<code class="computeroutput"><span class="keyword">int</span></code> is a valid value for <code class="computeroutput"><span class="string">"MaxValue"</span></code>, so we cannot jut use <code class="computeroutput"><span class="special">-</span><span class="number">1</span></code> to represent
|
||||||
|
the absence of the parameter in the config file.
|
||||||
|
</p>
|
||||||
|
<h4>
|
||||||
|
<a name="optional.introduction.h1"></a>
|
||||||
|
<span class="phrase"><a name="optional.introduction.solution"></a></span><a class="link" href="introduction.html#optional.introduction.solution">Solution</a>
|
||||||
|
</h4>
|
||||||
|
<p>
|
||||||
|
This is how you solve it with <code class="computeroutput"><span class="identifier">boost</span><span class="special">::</span><span class="identifier">optional</span></code>:
|
||||||
|
</p>
|
||||||
|
<pre class="programlisting"><span class="preprocessor">#include</span> <span class="special"><</span><span class="identifier">boost</span><span class="special">/</span><span class="identifier">optional</span><span class="special">.</span><span class="identifier">hpp</span><span class="special">></span>
|
||||||
|
|
||||||
|
<span class="identifier">boost</span><span class="special">::</span><span class="identifier">optional</span><span class="special"><</span><span class="keyword">int</span><span class="special">></span> <span class="identifier">getConfigParam</span><span class="special">(</span><span class="identifier">std</span><span class="special">::</span><span class="identifier">string</span> <span class="identifier">name</span><span class="special">);</span> <span class="comment">// return either an int or a `not-an-int`</span>
|
||||||
|
|
||||||
|
<span class="keyword">int</span> <span class="identifier">main</span><span class="special">()</span>
|
||||||
|
<span class="special">{</span>
|
||||||
|
<span class="keyword">if</span> <span class="special">(</span><span class="identifier">boost</span><span class="special">::</span><span class="identifier">optional</span><span class="special"><</span><span class="keyword">int</span><span class="special">></span> <span class="identifier">oi</span> <span class="special">=</span> <span class="identifier">getConfigParam</span><span class="special">(</span><span class="string">"MaxValue"</span><span class="special">))</span> <span class="comment">// did I get a real int?</span>
|
||||||
|
<span class="identifier">runWithMax</span><span class="special">(*</span><span class="identifier">oi</span><span class="special">);</span> <span class="comment">// use my int</span>
|
||||||
|
<span class="keyword">else</span>
|
||||||
|
<span class="identifier">runWithNoMax</span><span class="special">();</span>
|
||||||
|
<span class="special">}</span>
|
||||||
|
</pre>
|
||||||
|
</div>
|
||||||
|
<table xmlns:rev="http://www.cs.rpi.edu/~gregod/boost/tools/doc/revision" width="100%"><tr>
|
||||||
|
<td align="left"></td>
|
||||||
|
<td align="right"><div class="copyright-footer">Copyright © 2003-2007 Fernando Luis Cacciola Carballal<br>Copyright © 2014 Andrzej Krzemieński<p>
|
||||||
|
Distributed under the Boost Software License, Version 1.0. (See accompanying
|
||||||
|
file LICENSE_1_0.txt or copy at <a href="http://www.boost.org/LICENSE_1_0.txt" target="_top">http://www.boost.org/LICENSE_1_0.txt</a>)
|
||||||
|
</p>
|
||||||
|
</div></td>
|
||||||
|
</tr></table>
|
||||||
|
<hr>
|
||||||
|
<div class="spirit-nav">
|
||||||
|
<a accesskey="p" href="../index.html"><img src="../../../../../doc/src/images/prev.png" alt="Prev"></a><a accesskey="u" href="../index.html"><img src="../../../../../doc/src/images/up.png" alt="Up"></a><a accesskey="h" href="../index.html"><img src="../../../../../doc/src/images/home.png" alt="Home"></a><a accesskey="n" href="../boost_optional/quick_start.html"><img src="../../../../../doc/src/images/next.png" alt="Next"></a>
|
||||||
|
</div>
|
||||||
|
</body>
|
||||||
|
</html>
|
54
doc/html/optional/introduction/problem.html
Normal file
54
doc/html/optional/introduction/problem.html
Normal file
@ -0,0 +1,54 @@
|
|||||||
|
<html>
|
||||||
|
<head>
|
||||||
|
<meta http-equiv="Content-Type" content="text/html; charset=US-ASCII">
|
||||||
|
<title>Problem</title>
|
||||||
|
<link rel="stylesheet" href="../../../../../../doc/src/boostbook.css" type="text/css">
|
||||||
|
<meta name="generator" content="DocBook XSL Stylesheets V1.78.1">
|
||||||
|
<link rel="home" href="../../index.html" title="Chapter 1. Boost.Optional">
|
||||||
|
<link rel="up" href="../introduction.html" title="Introduction">
|
||||||
|
<link rel="prev" href="../introduction.html" title="Introduction">
|
||||||
|
<link rel="next" href="solution.html" title="Solution">
|
||||||
|
</head>
|
||||||
|
<body bgcolor="white" text="black" link="#0000FF" vlink="#840084" alink="#0000FF">
|
||||||
|
<table cellpadding="2" width="100%"><tr>
|
||||||
|
<td valign="top"><img alt="Boost C++ Libraries" width="277" height="86" src="../../../../../../boost.png"></td>
|
||||||
|
<td align="center"><a href="../../../../../../index.html">Home</a></td>
|
||||||
|
<td align="center"><a href="../../../../../../libs/libraries.htm">Libraries</a></td>
|
||||||
|
<td align="center"><a href="http://www.boost.org/users/people.html">People</a></td>
|
||||||
|
<td align="center"><a href="http://www.boost.org/users/faq.html">FAQ</a></td>
|
||||||
|
<td align="center"><a href="../../../../../../more/index.htm">More</a></td>
|
||||||
|
</tr></table>
|
||||||
|
<hr>
|
||||||
|
<div class="spirit-nav">
|
||||||
|
<a accesskey="p" href="../introduction.html"><img src="../../../../../../doc/src/images/prev.png" alt="Prev"></a><a accesskey="u" href="../introduction.html"><img src="../../../../../../doc/src/images/up.png" alt="Up"></a><a accesskey="h" href="../../index.html"><img src="../../../../../../doc/src/images/home.png" alt="Home"></a><a accesskey="n" href="solution.html"><img src="../../../../../../doc/src/images/next.png" alt="Next"></a>
|
||||||
|
</div>
|
||||||
|
<div class="section">
|
||||||
|
<div class="titlepage"><div><div><h3 class="title">
|
||||||
|
<a name="optional.introduction.problem"></a><a class="link" href="problem.html" title="Problem">Problem</a>
|
||||||
|
</h3></div></div></div>
|
||||||
|
<p>
|
||||||
|
Suppose we want to read a parameter form a config file which represents some
|
||||||
|
integral value, let's call it <code class="computeroutput"><span class="string">"MaxValue"</span></code>.
|
||||||
|
It is possible that this parameter is not specified; such situation is no
|
||||||
|
error. It is valid to not specify the parameter and in that case the program
|
||||||
|
is supposed to behave slightly different. Also suppose that any possible
|
||||||
|
value of type <code class="computeroutput"><span class="keyword">int</span></code> is a valid
|
||||||
|
value for <code class="computeroutput"><span class="string">"MaxValue"</span></code>,
|
||||||
|
so we cannot jut use <code class="computeroutput"><span class="special">-</span><span class="number">1</span></code>
|
||||||
|
to represent the absence of the parameter in the config file.
|
||||||
|
</p>
|
||||||
|
</div>
|
||||||
|
<table xmlns:rev="http://www.cs.rpi.edu/~gregod/boost/tools/doc/revision" width="100%"><tr>
|
||||||
|
<td align="left"></td>
|
||||||
|
<td align="right"><div class="copyright-footer">Copyright © 2003-2007 Fernando Luis Cacciola Carballal<br>Copyright © 2014 Andrzej Krzemieński<p>
|
||||||
|
Distributed under the Boost Software License, Version 1.0. (See accompanying
|
||||||
|
file LICENSE_1_0.txt or copy at <a href="http://www.boost.org/LICENSE_1_0.txt" target="_top">http://www.boost.org/LICENSE_1_0.txt</a>)
|
||||||
|
</p>
|
||||||
|
</div></td>
|
||||||
|
</tr></table>
|
||||||
|
<hr>
|
||||||
|
<div class="spirit-nav">
|
||||||
|
<a accesskey="p" href="../introduction.html"><img src="../../../../../../doc/src/images/prev.png" alt="Prev"></a><a accesskey="u" href="../introduction.html"><img src="../../../../../../doc/src/images/up.png" alt="Up"></a><a accesskey="h" href="../../index.html"><img src="../../../../../../doc/src/images/home.png" alt="Home"></a><a accesskey="n" href="solution.html"><img src="../../../../../../doc/src/images/next.png" alt="Next"></a>
|
||||||
|
</div>
|
||||||
|
</body>
|
||||||
|
</html>
|
58
doc/html/optional/introduction/solution.html
Normal file
58
doc/html/optional/introduction/solution.html
Normal file
@ -0,0 +1,58 @@
|
|||||||
|
<html>
|
||||||
|
<head>
|
||||||
|
<meta http-equiv="Content-Type" content="text/html; charset=US-ASCII">
|
||||||
|
<title>Solution</title>
|
||||||
|
<link rel="stylesheet" href="../../../../../../doc/src/boostbook.css" type="text/css">
|
||||||
|
<meta name="generator" content="DocBook XSL Stylesheets V1.78.1">
|
||||||
|
<link rel="home" href="../../index.html" title="Chapter 1. Boost.Optional">
|
||||||
|
<link rel="up" href="../introduction.html" title="Introduction">
|
||||||
|
<link rel="prev" href="problem.html" title="Problem">
|
||||||
|
<link rel="next" href="../../boost_optional/quick_start.html" title="Quick Start">
|
||||||
|
</head>
|
||||||
|
<body bgcolor="white" text="black" link="#0000FF" vlink="#840084" alink="#0000FF">
|
||||||
|
<table cellpadding="2" width="100%"><tr>
|
||||||
|
<td valign="top"><img alt="Boost C++ Libraries" width="277" height="86" src="../../../../../../boost.png"></td>
|
||||||
|
<td align="center"><a href="../../../../../../index.html">Home</a></td>
|
||||||
|
<td align="center"><a href="../../../../../../libs/libraries.htm">Libraries</a></td>
|
||||||
|
<td align="center"><a href="http://www.boost.org/users/people.html">People</a></td>
|
||||||
|
<td align="center"><a href="http://www.boost.org/users/faq.html">FAQ</a></td>
|
||||||
|
<td align="center"><a href="../../../../../../more/index.htm">More</a></td>
|
||||||
|
</tr></table>
|
||||||
|
<hr>
|
||||||
|
<div class="spirit-nav">
|
||||||
|
<a accesskey="p" href="problem.html"><img src="../../../../../../doc/src/images/prev.png" alt="Prev"></a><a accesskey="u" href="../introduction.html"><img src="../../../../../../doc/src/images/up.png" alt="Up"></a><a accesskey="h" href="../../index.html"><img src="../../../../../../doc/src/images/home.png" alt="Home"></a><a accesskey="n" href="../../boost_optional/quick_start.html"><img src="../../../../../../doc/src/images/next.png" alt="Next"></a>
|
||||||
|
</div>
|
||||||
|
<div class="section">
|
||||||
|
<div class="titlepage"><div><div><h3 class="title">
|
||||||
|
<a name="optional.introduction.solution"></a><a class="link" href="solution.html" title="Solution">Solution</a>
|
||||||
|
</h3></div></div></div>
|
||||||
|
<p>
|
||||||
|
This is how you solve it with <code class="computeroutput"><span class="identifier">boost</span><span class="special">::</span><span class="identifier">optional</span></code>:
|
||||||
|
</p>
|
||||||
|
<pre class="programlisting"><span class="preprocessor">#include</span> <span class="special"><</span><span class="identifier">boost</span><span class="special">/</span><span class="identifier">optional</span><span class="special">.</span><span class="identifier">hpp</span><span class="special">></span>
|
||||||
|
|
||||||
|
<span class="identifier">boost</span><span class="special">::</span><span class="identifier">optional</span><span class="special"><</span><span class="keyword">int</span><span class="special">></span> <span class="identifier">getConfigParam</span><span class="special">(</span><span class="identifier">std</span><span class="special">::</span><span class="identifier">string</span> <span class="identifier">name</span><span class="special">);</span> <span class="comment">// return either an int or a `not-an-int`</span>
|
||||||
|
|
||||||
|
<span class="keyword">int</span> <span class="identifier">main</span><span class="special">()</span>
|
||||||
|
<span class="special">{</span>
|
||||||
|
<span class="keyword">if</span> <span class="special">(</span><span class="identifier">boost</span><span class="special">::</span><span class="identifier">optional</span><span class="special"><</span><span class="keyword">int</span><span class="special">></span> <span class="identifier">oi</span> <span class="special">=</span> <span class="identifier">getConfigParam</span><span class="special">(</span><span class="string">"MaxValue"</span><span class="special">))</span> <span class="comment">// did I get a real int?</span>
|
||||||
|
<span class="identifier">runWithMax</span><span class="special">(*</span><span class="identifier">oi</span><span class="special">);</span> <span class="comment">// use my int</span>
|
||||||
|
<span class="keyword">else</span>
|
||||||
|
<span class="identifier">runWithNoMax</span><span class="special">();</span>
|
||||||
|
<span class="special">}</span>
|
||||||
|
</pre>
|
||||||
|
</div>
|
||||||
|
<table xmlns:rev="http://www.cs.rpi.edu/~gregod/boost/tools/doc/revision" width="100%"><tr>
|
||||||
|
<td align="left"></td>
|
||||||
|
<td align="right"><div class="copyright-footer">Copyright © 2003-2007 Fernando Luis Cacciola Carballal<br>Copyright © 2014 Andrzej Krzemieński<p>
|
||||||
|
Distributed under the Boost Software License, Version 1.0. (See accompanying
|
||||||
|
file LICENSE_1_0.txt or copy at <a href="http://www.boost.org/LICENSE_1_0.txt" target="_top">http://www.boost.org/LICENSE_1_0.txt</a>)
|
||||||
|
</p>
|
||||||
|
</div></td>
|
||||||
|
</tr></table>
|
||||||
|
<hr>
|
||||||
|
<div class="spirit-nav">
|
||||||
|
<a accesskey="p" href="problem.html"><img src="../../../../../../doc/src/images/prev.png" alt="Prev"></a><a accesskey="u" href="../introduction.html"><img src="../../../../../../doc/src/images/up.png" alt="Up"></a><a accesskey="h" href="../../index.html"><img src="../../../../../../doc/src/images/home.png" alt="Home"></a><a accesskey="n" href="../../boost_optional/quick_start.html"><img src="../../../../../../doc/src/images/next.png" alt="Next"></a>
|
||||||
|
</div>
|
||||||
|
</body>
|
||||||
|
</html>
|
48
doc/html/optional/reference.html
Normal file
48
doc/html/optional/reference.html
Normal file
@ -0,0 +1,48 @@
|
|||||||
|
<html>
|
||||||
|
<head>
|
||||||
|
<meta http-equiv="Content-Type" content="text/html; charset=US-ASCII">
|
||||||
|
<title>Reference</title>
|
||||||
|
<link rel="stylesheet" href="../../../../../doc/src/boostbook.css" type="text/css">
|
||||||
|
<meta name="generator" content="DocBook XSL Stylesheets V1.78.1">
|
||||||
|
<link rel="home" href="../index.html" title="Chapter 1. Boost.Optional">
|
||||||
|
<link rel="up" href="../index.html" title="Chapter 1. Boost.Optional">
|
||||||
|
<link rel="prev" href="../boost_optional/tutorial/type_requirements.html" title="Type requirements">
|
||||||
|
<link rel="next" href="../boost_optional/reference/synopsis.html" title="Synopsis">
|
||||||
|
</head>
|
||||||
|
<body bgcolor="white" text="black" link="#0000FF" vlink="#840084" alink="#0000FF">
|
||||||
|
<table cellpadding="2" width="100%"><tr>
|
||||||
|
<td valign="top"><img alt="Boost C++ Libraries" width="277" height="86" src="../../../../../boost.png"></td>
|
||||||
|
<td align="center"><a href="../../../../../index.html">Home</a></td>
|
||||||
|
<td align="center"><a href="../../../../../libs/libraries.htm">Libraries</a></td>
|
||||||
|
<td align="center"><a href="http://www.boost.org/users/people.html">People</a></td>
|
||||||
|
<td align="center"><a href="http://www.boost.org/users/faq.html">FAQ</a></td>
|
||||||
|
<td align="center"><a href="../../../../../more/index.htm">More</a></td>
|
||||||
|
</tr></table>
|
||||||
|
<hr>
|
||||||
|
<div class="spirit-nav">
|
||||||
|
<a accesskey="p" href="../boost_optional/tutorial/type_requirements.html"><img src="../../../../../doc/src/images/prev.png" alt="Prev"></a><a accesskey="u" href="../index.html"><img src="../../../../../doc/src/images/up.png" alt="Up"></a><a accesskey="h" href="../index.html"><img src="../../../../../doc/src/images/home.png" alt="Home"></a><a accesskey="n" href="../boost_optional/reference/synopsis.html"><img src="../../../../../doc/src/images/next.png" alt="Next"></a>
|
||||||
|
</div>
|
||||||
|
<div class="section">
|
||||||
|
<div class="titlepage"><div><div><h2 class="title" style="clear: both">
|
||||||
|
<a name="optional.reference"></a><a class="link" href="reference.html" title="Reference">Reference</a>
|
||||||
|
</h2></div></div></div>
|
||||||
|
<div class="toc"><dl class="toc">
|
||||||
|
<dt><span class="section"><a href="../boost_optional/reference/synopsis.html">Synopsis</a></span></dt>
|
||||||
|
<dt><span class="section"><a href="../boost_optional/reference/detailed_semantics.html">Detailed
|
||||||
|
Semantics</a></span></dt>
|
||||||
|
</dl></div>
|
||||||
|
</div>
|
||||||
|
<table xmlns:rev="http://www.cs.rpi.edu/~gregod/boost/tools/doc/revision" width="100%"><tr>
|
||||||
|
<td align="left"></td>
|
||||||
|
<td align="right"><div class="copyright-footer">Copyright © 2003-2007 Fernando Luis Cacciola Carballal<br>Copyright © 2014 Andrzej Krzemieński<p>
|
||||||
|
Distributed under the Boost Software License, Version 1.0. (See accompanying
|
||||||
|
file LICENSE_1_0.txt or copy at <a href="http://www.boost.org/LICENSE_1_0.txt" target="_top">http://www.boost.org/LICENSE_1_0.txt</a>)
|
||||||
|
</p>
|
||||||
|
</div></td>
|
||||||
|
</tr></table>
|
||||||
|
<hr>
|
||||||
|
<div class="spirit-nav">
|
||||||
|
<a accesskey="p" href="../boost_optional/tutorial/type_requirements.html"><img src="../../../../../doc/src/images/prev.png" alt="Prev"></a><a accesskey="u" href="../index.html"><img src="../../../../../doc/src/images/up.png" alt="Up"></a><a accesskey="h" href="../index.html"><img src="../../../../../doc/src/images/home.png" alt="Home"></a><a accesskey="n" href="../boost_optional/reference/synopsis.html"><img src="../../../../../doc/src/images/next.png" alt="Next"></a>
|
||||||
|
</div>
|
||||||
|
</body>
|
||||||
|
</html>
|
58
doc/html/optional/tutorial.html
Normal file
58
doc/html/optional/tutorial.html
Normal file
@ -0,0 +1,58 @@
|
|||||||
|
<html>
|
||||||
|
<head>
|
||||||
|
<meta http-equiv="Content-Type" content="text/html; charset=US-ASCII">
|
||||||
|
<title>Tutorial</title>
|
||||||
|
<link rel="stylesheet" href="../../../../../doc/src/boostbook.css" type="text/css">
|
||||||
|
<meta name="generator" content="DocBook XSL Stylesheets V1.78.1">
|
||||||
|
<link rel="home" href="../index.html" title="Chapter 1. Boost.Optional">
|
||||||
|
<link rel="up" href="../index.html" title="Chapter 1. Boost.Optional">
|
||||||
|
<link rel="prev" href="../boost_optional/quick_start.html" title="Quick Start">
|
||||||
|
<link rel="next" href="../boost_optional/tutorial/motivation.html" title="Motivation">
|
||||||
|
</head>
|
||||||
|
<body bgcolor="white" text="black" link="#0000FF" vlink="#840084" alink="#0000FF">
|
||||||
|
<table cellpadding="2" width="100%"><tr>
|
||||||
|
<td valign="top"><img alt="Boost C++ Libraries" width="277" height="86" src="../../../../../boost.png"></td>
|
||||||
|
<td align="center"><a href="../../../../../index.html">Home</a></td>
|
||||||
|
<td align="center"><a href="../../../../../libs/libraries.htm">Libraries</a></td>
|
||||||
|
<td align="center"><a href="http://www.boost.org/users/people.html">People</a></td>
|
||||||
|
<td align="center"><a href="http://www.boost.org/users/faq.html">FAQ</a></td>
|
||||||
|
<td align="center"><a href="../../../../../more/index.htm">More</a></td>
|
||||||
|
</tr></table>
|
||||||
|
<hr>
|
||||||
|
<div class="spirit-nav">
|
||||||
|
<a accesskey="p" href="../boost_optional/quick_start.html"><img src="../../../../../doc/src/images/prev.png" alt="Prev"></a><a accesskey="u" href="../index.html"><img src="../../../../../doc/src/images/up.png" alt="Up"></a><a accesskey="h" href="../index.html"><img src="../../../../../doc/src/images/home.png" alt="Home"></a><a accesskey="n" href="../boost_optional/tutorial/motivation.html"><img src="../../../../../doc/src/images/next.png" alt="Next"></a>
|
||||||
|
</div>
|
||||||
|
<div class="section">
|
||||||
|
<div class="titlepage"><div><div><h2 class="title" style="clear: both">
|
||||||
|
<a name="optional.tutorial"></a><a class="link" href="tutorial.html" title="Tutorial">Tutorial</a>
|
||||||
|
</h2></div></div></div>
|
||||||
|
<div class="toc"><dl class="toc">
|
||||||
|
<dt><span class="section"><a href="../boost_optional/tutorial/motivation.html">Motivation</a></span></dt>
|
||||||
|
<dt><span class="section"><a href="../boost_optional/tutorial/design_overview.html">Design Overview</a></span></dt>
|
||||||
|
<dt><span class="section"><a href="../boost_optional/tutorial/optional_references.html">Optional
|
||||||
|
references</a></span></dt>
|
||||||
|
<dt><span class="section"><a href="../boost_optional/tutorial/rebinding_semantics_for_assignment_of_optional_references.html">Rebinding
|
||||||
|
semantics for assignment of optional references</a></span></dt>
|
||||||
|
<dt><span class="section"><a href="../boost_optional/tutorial/in_place_factories.html">In-Place
|
||||||
|
Factories</a></span></dt>
|
||||||
|
<dt><span class="section"><a href="../boost_optional/tutorial/a_note_about_optional_bool_.html">A
|
||||||
|
note about optional<bool></a></span></dt>
|
||||||
|
<dt><span class="section"><a href="../boost_optional/tutorial/exception_safety_guarantees.html">Exception
|
||||||
|
Safety Guarantees</a></span></dt>
|
||||||
|
<dt><span class="section"><a href="../boost_optional/tutorial/type_requirements.html">Type requirements</a></span></dt>
|
||||||
|
</dl></div>
|
||||||
|
</div>
|
||||||
|
<table xmlns:rev="http://www.cs.rpi.edu/~gregod/boost/tools/doc/revision" width="100%"><tr>
|
||||||
|
<td align="left"></td>
|
||||||
|
<td align="right"><div class="copyright-footer">Copyright © 2003-2007 Fernando Luis Cacciola Carballal<br>Copyright © 2014 Andrzej Krzemieński<p>
|
||||||
|
Distributed under the Boost Software License, Version 1.0. (See accompanying
|
||||||
|
file LICENSE_1_0.txt or copy at <a href="http://www.boost.org/LICENSE_1_0.txt" target="_top">http://www.boost.org/LICENSE_1_0.txt</a>)
|
||||||
|
</p>
|
||||||
|
</div></td>
|
||||||
|
</tr></table>
|
||||||
|
<hr>
|
||||||
|
<div class="spirit-nav">
|
||||||
|
<a accesskey="p" href="../boost_optional/quick_start.html"><img src="../../../../../doc/src/images/prev.png" alt="Prev"></a><a accesskey="u" href="../index.html"><img src="../../../../../doc/src/images/up.png" alt="Up"></a><a accesskey="h" href="../index.html"><img src="../../../../../doc/src/images/home.png" alt="Home"></a><a accesskey="n" href="../boost_optional/tutorial/motivation.html"><img src="../../../../../doc/src/images/next.png" alt="Next"></a>
|
||||||
|
</div>
|
||||||
|
</body>
|
||||||
|
</html>
|
@ -151,6 +151,7 @@ struct types_when_isnt_ref
|
|||||||
typedef T & reference_type ;
|
typedef T & reference_type ;
|
||||||
#ifndef BOOST_NO_CXX11_RVALUE_REFERENCES
|
#ifndef BOOST_NO_CXX11_RVALUE_REFERENCES
|
||||||
typedef T && rval_reference_type ;
|
typedef T && rval_reference_type ;
|
||||||
|
typedef T && reference_type_of_temporary_wrapper;
|
||||||
#ifdef BOOST_MOVE_OLD_RVALUE_REF_BINDING_RULES
|
#ifdef BOOST_MOVE_OLD_RVALUE_REF_BINDING_RULES
|
||||||
// GCC 4.4 has support for an early draft of rvalue references. The conforming version below
|
// GCC 4.4 has support for an early draft of rvalue references. The conforming version below
|
||||||
// causes warnings about returning references to a temporary.
|
// causes warnings about returning references to a temporary.
|
||||||
@ -173,6 +174,7 @@ struct types_when_is_ref
|
|||||||
typedef raw_type& reference_type ;
|
typedef raw_type& reference_type ;
|
||||||
#ifndef BOOST_NO_CXX11_RVALUE_REFERENCES
|
#ifndef BOOST_NO_CXX11_RVALUE_REFERENCES
|
||||||
typedef BOOST_DEDUCED_TYPENAME remove_const<raw_type>::type&& rval_reference_type ;
|
typedef BOOST_DEDUCED_TYPENAME remove_const<raw_type>::type&& rval_reference_type ;
|
||||||
|
typedef raw_type& reference_type_of_temporary_wrapper;
|
||||||
static reference_type move(reference_type r) { return r; }
|
static reference_type move(reference_type r) { return r; }
|
||||||
#endif
|
#endif
|
||||||
typedef raw_type* pointer_const_type ;
|
typedef raw_type* pointer_const_type ;
|
||||||
@ -227,6 +229,7 @@ class optional_base : public optional_tag
|
|||||||
typedef BOOST_DEDUCED_TYPENAME types::reference_const_type reference_const_type ;
|
typedef BOOST_DEDUCED_TYPENAME types::reference_const_type reference_const_type ;
|
||||||
#ifndef BOOST_NO_CXX11_RVALUE_REFERENCES
|
#ifndef BOOST_NO_CXX11_RVALUE_REFERENCES
|
||||||
typedef BOOST_DEDUCED_TYPENAME types::rval_reference_type rval_reference_type ;
|
typedef BOOST_DEDUCED_TYPENAME types::rval_reference_type rval_reference_type ;
|
||||||
|
typedef BOOST_DEDUCED_TYPENAME types::reference_type_of_temporary_wrapper reference_type_of_temporary_wrapper ;
|
||||||
#endif
|
#endif
|
||||||
typedef BOOST_DEDUCED_TYPENAME types::pointer_type pointer_type ;
|
typedef BOOST_DEDUCED_TYPENAME types::pointer_type pointer_type ;
|
||||||
typedef BOOST_DEDUCED_TYPENAME types::pointer_const_type pointer_const_type ;
|
typedef BOOST_DEDUCED_TYPENAME types::pointer_const_type pointer_const_type ;
|
||||||
@ -725,6 +728,7 @@ class optional : public optional_detail::optional_base<T>
|
|||||||
typedef BOOST_DEDUCED_TYPENAME base::reference_const_type reference_const_type ;
|
typedef BOOST_DEDUCED_TYPENAME base::reference_const_type reference_const_type ;
|
||||||
#ifndef BOOST_NO_CXX11_RVALUE_REFERENCES
|
#ifndef BOOST_NO_CXX11_RVALUE_REFERENCES
|
||||||
typedef BOOST_DEDUCED_TYPENAME base::rval_reference_type rval_reference_type ;
|
typedef BOOST_DEDUCED_TYPENAME base::rval_reference_type rval_reference_type ;
|
||||||
|
typedef BOOST_DEDUCED_TYPENAME base::reference_type_of_temporary_wrapper reference_type_of_temporary_wrapper ;
|
||||||
#endif
|
#endif
|
||||||
typedef BOOST_DEDUCED_TYPENAME base::pointer_type pointer_type ;
|
typedef BOOST_DEDUCED_TYPENAME base::pointer_type pointer_type ;
|
||||||
typedef BOOST_DEDUCED_TYPENAME base::pointer_const_type pointer_const_type ;
|
typedef BOOST_DEDUCED_TYPENAME base::pointer_const_type pointer_const_type ;
|
||||||
@ -961,7 +965,7 @@ class optional : public optional_detail::optional_base<T>
|
|||||||
#ifndef BOOST_NO_CXX11_REF_QUALIFIERS
|
#ifndef BOOST_NO_CXX11_REF_QUALIFIERS
|
||||||
reference_const_type operator *() const& { return this->get() ; }
|
reference_const_type operator *() const& { return this->get() ; }
|
||||||
reference_type operator *() & { return this->get() ; }
|
reference_type operator *() & { return this->get() ; }
|
||||||
rval_reference_type operator *() && { return boost::move(this->get()) ; }
|
reference_type_of_temporary_wrapper operator *() && { return boost::move(this->get()) ; }
|
||||||
#else
|
#else
|
||||||
reference_const_type operator *() const { return this->get() ; }
|
reference_const_type operator *() const { return this->get() ; }
|
||||||
reference_type operator *() { return this->get() ; }
|
reference_type operator *() { return this->get() ; }
|
||||||
@ -984,7 +988,7 @@ class optional : public optional_detail::optional_base<T>
|
|||||||
throw_exception(bad_optional_access("Attempted to access the value of an uninitialized optional object."));
|
throw_exception(bad_optional_access("Attempted to access the value of an uninitialized optional object."));
|
||||||
}
|
}
|
||||||
|
|
||||||
rval_reference_type value() &&
|
reference_type_of_temporary_wrapper value() &&
|
||||||
{
|
{
|
||||||
if (this->is_initialized())
|
if (this->is_initialized())
|
||||||
return boost::move(this->get()) ;
|
return boost::move(this->get()) ;
|
||||||
|
Reference in New Issue
Block a user