Compare commits

..

1 Commits

Author SHA1 Message Date
302e6ba9f9 This commit was manufactured by cvs2svn to create branch 'SPIRIT_1_6'.
[SVN r23968]
2004-07-23 02:16:28 +00:00
6 changed files with 212 additions and 96 deletions

View File

@ -0,0 +1,56 @@
// Copyright (C) 2003, Fernando Luis Cacciola Carballal.
//
// Use, modification, and distribution is subject to 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)
//
// See http://www.boost.org/lib/optional for documentation.
//
// You are welcome to contact the author at:
// fernando_cacciola@hotmail.com
//
#ifndef BOOST_UTILITY_INPLACE_FACTORY_25AGO2003_HPP
#define BOOST_UTILITY_INPLACE_FACTORY_25AGO2003_HPP
#include <boost/detail/in_place_factory_prefix.hpp>
#include <boost/type.hpp>
namespace boost {
class InPlaceFactoryBase {} ;
#define BOOST_DEFINE_INPLACE_FACTORY_CLASS(z,n,_) \
template< BOOST_PP_ENUM_PARAMS(BOOST_PP_INC(n),class A) > \
class BOOST_PP_CAT(InPlaceFactory, BOOST_PP_INC(n) ) : public InPlaceFactoryBase \
{ \
public: \
\
BOOST_PP_CAT(InPlaceFactory, BOOST_PP_INC(n) ) ( BOOST_PP_ENUM_BINARY_PARAMS(BOOST_PP_INC(n),A,const& a) ) \
: \
BOOST_PP_ENUM( BOOST_PP_INC(n), BOOST_DEFINE_INPLACE_FACTORY_CLASS_MEMBER_INIT, _ ) \
{} \
\
template<class T> \
void apply ( void* address BOOST_APPEND_EXPLICIT_TEMPLATE_TYPE(T) ) const \
{ \
new ( address ) T ( BOOST_PP_ENUM_PARAMS( BOOST_PP_INC(n), m_a ) ) ; \
} \
\
BOOST_PP_REPEAT( BOOST_PP_INC(n), BOOST_DEFINE_INPLACE_FACTORY_CLASS_MEMBER_DECL, _) \
} ; \
\
template< BOOST_PP_ENUM_PARAMS(BOOST_PP_INC(n),class A) > \
BOOST_PP_CAT(InPlaceFactory, BOOST_PP_INC(n) ) < BOOST_PP_ENUM_PARAMS( BOOST_PP_INC(n), A ) > \
in_place ( BOOST_PP_ENUM_BINARY_PARAMS(BOOST_PP_INC(n),A, const& a) ) \
{ \
return BOOST_PP_CAT(InPlaceFactory, BOOST_PP_INC(n) ) < BOOST_PP_ENUM_PARAMS( BOOST_PP_INC(n), A ) > \
( BOOST_PP_ENUM_PARAMS( BOOST_PP_INC(n), a ) ) ; \
} ; \
BOOST_PP_REPEAT( BOOST_MAX_INPLACE_FACTORY_ARITY, BOOST_DEFINE_INPLACE_FACTORY_CLASS, BOOST_PP_EMPTY() )
} // namespace boost
#endif

View File

@ -0,0 +1,33 @@
// Copyright (C) 2003, Fernando Luis Cacciola Carballal.
//
// Use, modification, and distribution is subject to 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)
//
// See http://www.boost.org/lib/optional for documentation.
//
// You are welcome to contact the author at:
// fernando_cacciola@hotmail.com
//
#ifndef BOOST_UTILITY_INPLACE_FACTORY_PREFIX_25AGO2003_HPP
#define BOOST_UTILITY_INPLACE_FACTORY_PREFIX_25AGO2003_HPP
#include <boost/config.hpp>
#include <boost/preprocessor/repetition/enum.hpp>
#include <boost/preprocessor/repetition/enum_params.hpp>
#include <boost/preprocessor/repetition/enum_binary_params.hpp>
#include <boost/preprocessor/cat.hpp>
#include <boost/preprocessor/arithmetic/inc.hpp>
#include <boost/preprocessor/punctuation/paren.hpp>
#include <boost/preprocessor/facilities/empty.hpp>
#define BOOST_DEFINE_INPLACE_FACTORY_CLASS_MEMBER_INIT(z,n,_) BOOST_PP_CAT(m_a,n) BOOST_PP_LPAREN() BOOST_PP_CAT(a,n) BOOST_PP_RPAREN()
#define BOOST_DEFINE_INPLACE_FACTORY_CLASS_MEMBER_DECL(z,n,_) BOOST_PP_CAT(A,n) const& BOOST_PP_CAT(m_a,n);
#define BOOST_DEFINE_INPLACE_FACTORY_CLASS_MEMBER_ARG(z,n,_) BOOST_PP_CAT(m_a,n)
#define BOOST_MAX_INPLACE_FACTORY_ARITY 10
#undef BOOST_UTILITY_INPLACE_FACTORY_SUFFIX_25AGO2003_HPP
#endif

View File

@ -9,16 +9,15 @@
// You are welcome to contact the author at:
// fernando_cacciola@hotmail.com
//
#ifndef BOOST_NONE_T_17SEP2003_HPP
#define BOOST_NONE_T_17SEP2003_HPP
#ifndef BOOST_UTILITY_INPLACE_FACTORY_SUFFIX_25AGO2003_HPP
#define BOOST_UTILITY_INPLACE_FACTORY_SUFFIX_25AGO2003_HPP
namespace boost {
#undef BOOST_DEFINE_INPLACE_FACTORY_CLASS_MEMBER_INIT
#undef BOOST_DEFINE_INPLACE_FACTORY_CLASS_MEMBER_DECL
#undef BOOST_DEFINE_INPLACE_FACTORY_CLASS_MEMBER_ARG
#undef BOOST_MAX_INPLACE_FACTORY_ARITY
namespace detail { struct none_helper{}; }
typedef int detail::none_helper::*none_t ;
} // namespace boost
#undef BOOST_UTILITY_INPLACE_FACTORY_PREFIX_25AGO2003_HPP
#endif

View File

@ -0,0 +1,57 @@
// Copyright (C) 2003, Fernando Luis Cacciola Carballal.
//
// Use, modification, and distribution is subject to 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)
//
// See http://www.boost.org/lib/optional for documentation.
//
// You are welcome to contact the author at:
// fernando_cacciola@hotmail.com
//
#ifndef BOOST_UTILITY_TYPED_INPLACE_FACTORY_25AGO2003_HPP
#define BOOST_UTILITY_TYPED_INPLACE_FACTORY_25AGO2003_HPP
#include <boost/detail/in_place_factory_prefix.hpp>
namespace boost {
class TypedInPlaceFactoryBase {} ;
#define BOOST_DEFINE_TYPED_INPLACE_FACTORY_CLASS(z,n,_) \
template< class T, BOOST_PP_ENUM_PARAMS(BOOST_PP_INC(n),class A) > \
class BOOST_PP_CAT(TypedInPlaceFactory, BOOST_PP_INC(n) ) : public TypedInPlaceFactoryBase \
{ \
public: \
\
typedef T value_type ; \
\
BOOST_PP_CAT(TypedInPlaceFactory, BOOST_PP_INC(n) ) ( BOOST_PP_ENUM_BINARY_PARAMS(BOOST_PP_INC(n),A,const& a) ) \
: \
BOOST_PP_ENUM( BOOST_PP_INC(n), BOOST_DEFINE_INPLACE_FACTORY_CLASS_MEMBER_INIT, _ ) \
{} \
\
void apply ( void* address ) const \
{ \
new ( address ) T ( BOOST_PP_ENUM_PARAMS( BOOST_PP_INC(n), m_a ) ) ; \
} \
\
BOOST_PP_REPEAT( BOOST_PP_INC(n), BOOST_DEFINE_INPLACE_FACTORY_CLASS_MEMBER_DECL, _) \
} ; \
\
template< class T, BOOST_PP_ENUM_PARAMS(BOOST_PP_INC(n),class A) > \
BOOST_PP_CAT(TypedInPlaceFactory, BOOST_PP_INC(n) ) < T , BOOST_PP_ENUM_PARAMS( BOOST_PP_INC(n), A ) > \
in_place ( BOOST_PP_ENUM_BINARY_PARAMS(BOOST_PP_INC(n),A, const& a) ) \
{ \
return BOOST_PP_CAT(TypedInPlaceFactory, BOOST_PP_INC(n) ) < T, BOOST_PP_ENUM_PARAMS( BOOST_PP_INC(n), A ) > \
( BOOST_PP_ENUM_PARAMS( BOOST_PP_INC(n), a ) ) ; \
} ; \
BOOST_PP_REPEAT( BOOST_MAX_INPLACE_FACTORY_ARITY, BOOST_DEFINE_TYPED_INPLACE_FACTORY_CLASS, BOOST_PP_EMPTY() )
} // namespace boost
#include <boost/detail/in_place_factory_suffix.hpp>
#endif

View File

@ -12,7 +12,7 @@
#ifndef BOOST_NONE_17SEP2003_HPP
#define BOOST_NONE_17SEP2003_HPP
#include "boost/none_t.hpp"
#include "boost/detail/none_t.hpp"
// NOTE: Borland users have to include this header outside any precompiled headers
// (bcc<=5.64 cannot include instance data in a precompiled header)
@ -21,7 +21,7 @@ namespace boost {
namespace {
none_t const none = ((none_t)0) ;
detail::none_t const none = ((detail::none_t)0) ;
}

View File

@ -26,10 +26,10 @@
#include "boost/mpl/bool.hpp"
#include "boost/mpl/not.hpp"
#include "boost/detail/reference_content.hpp"
#include "boost/none_t.hpp"
#include "boost/detail/none_t.hpp"
#include "boost/utility/compare_pointees.hpp"
#if BOOST_WORKAROUND(BOOST_MSVC, < 1300)
#if BOOST_WORKAROUND(BOOST_MSVC, == 1200)
// VC6.0 has the following bug:
// When a templated assignment operator exist, an implicit conversion
// constructing an optional<T> is used when assigment of the form:
@ -77,8 +77,8 @@
namespace boost {
class in_place_factory_base ;
class typed_in_place_factory_base ;
class InPlaceFactoryBase ;
class TypedInPlaceFactoryBase ;
namespace optional_detail {
@ -143,7 +143,7 @@ class optional_base : public optional_tag
protected :
typedef T value_type ;
typedef mpl::true_ is_reference_tag ;
typedef mpl::false_ is_not_reference_tag ;
@ -167,7 +167,7 @@ class optional_base : public optional_tag
// Creates an optional<T> uninitialized.
// No-throw
optional_base ( none_t const& )
optional_base ( detail::none_t const& )
:
m_initialized(false) {}
@ -190,7 +190,7 @@ class optional_base : public optional_tag
construct(rhs.get_impl());
}
// This is used for both converting and in-place constructions.
// Derived classes use the 'tag' to select the appropriate
// implementation (the correct 'construct()' overload)
@ -202,46 +202,38 @@ class optional_base : public optional_tag
construct(expr,tag);
}
// No-throw (assuming T::~T() doesn't)
~optional_base() { destroy() ; }
// Assigns from another optional<T> (deep-copies the rhs value)
// Basic Guarantee: If T::T( T const& ) throws, this is left UNINITIALIZED
void assign ( optional_base const& rhs )
{
if (is_initialized())
{
if ( rhs.is_initialized() )
assign_value(rhs.get_impl(), is_reference_predicate() );
else destroy();
}
else
{
destroy();
if ( rhs.is_initialized() )
construct(rhs.get_impl());
}
}
// Assigns from a T (deep-copies the rhs value)
// Basic Guarantee: If T::( T const& ) throws, this is left UNINITIALIZED
void assign ( argument_type val )
{
if (is_initialized())
assign_value(val, is_reference_predicate() );
else construct(val);
}
{
destroy();
construct(val);
}
// Assigns from "none", destroying the current value, if any, leaving this UNINITIALIZED
// No-throw (assuming T::~T() doesn't)
void assign ( none_t const& ) { destroy(); }
void assign ( detail::none_t const& ) { destroy(); }
#ifndef BOOST_OPTIONAL_NO_INPLACE_FACTORY_SUPPORT
template<class Expr>
void assign_expr ( Expr const& expr, Expr const* tag )
void assign_expr ( Expr const& expr, Expr const* tag )
{
if (is_initialized())
assign_expr_to_initialized(expr,tag);
else construct(expr,tag);
destroy();
construct(expr,tag);
}
#endif
@ -252,6 +244,7 @@ class optional_base : public optional_tag
void reset() { destroy(); }
// Replaces the current value -if any- with 'val'
// Basic Guarantee: If T::T( T const& ) throws this is left UNINITIALIZED.
void reset ( argument_type val ) { assign(val); }
// Returns a pointer to the value if this is initialized, otherwise,
@ -273,7 +266,7 @@ class optional_base : public optional_tag
#ifndef BOOST_OPTIONAL_NO_INPLACE_FACTORY_SUPPORT
// Constructs in-place using the given factory
template<class Expr>
void construct ( Expr const& factory, in_place_factory_base const* )
void construct ( Expr const& factory, InPlaceFactoryBase const* )
{
BOOST_STATIC_ASSERT ( ::boost::mpl::not_<is_reference_predicate>::value ) ;
factory.BOOST_NESTED_TEMPLATE apply<value_type>(m_storage.address()) ;
@ -282,27 +275,12 @@ class optional_base : public optional_tag
// Constructs in-place using the given typed factory
template<class Expr>
void construct ( Expr const& factory, typed_in_place_factory_base const* )
void construct ( Expr const& factory, TypedInPlaceFactoryBase const* )
{
BOOST_STATIC_ASSERT ( ::boost::mpl::not_<is_reference_predicate>::value ) ;
factory.apply(m_storage.address()) ;
m_initialized = true ;
}
template<class Expr>
void assign_expr_to_initialized ( Expr const& factory, in_place_factory_base const* tag )
{
destroy();
construct(factory,tag);
}
// Constructs in-place using the given typed factory
template<class Expr>
void assign_expr_to_initialized ( Expr const& factory, typed_in_place_factory_base const* tag )
{
destroy();
construct(factory,tag);
}
#endif
// Constructs using any expression implicitely convertible to the single argument
@ -316,16 +294,6 @@ class optional_base : public optional_tag
m_initialized = true ;
}
// Assigns using a form any expression implicitely convertible to the single argument
// of a T's assignment operator.
// Converting assignments of optional<T> from optional<U> uses this function with
// 'Expr' being of type 'U' and relying on a converting assignment of T from U.
template<class Expr>
void assign_expr_to_initialized ( Expr const& expr, void const* )
{
assign_value(expr, is_reference_predicate());
}
#ifdef BOOST_OPTIONAL_WEAK_OVERLOAD_RESOLUTION
// BCB5.64 (and probably lower versions) workaround.
// The in-place factories are supported by means of catch-all constructors
@ -353,14 +321,11 @@ class optional_base : public optional_tag
}
#endif
void assign_value ( argument_type val, is_not_reference_tag ) { get_impl() = val; }
void assign_value ( argument_type val, is_reference_tag ) { construct(val); }
void destroy()
{
if ( m_initialized )
destroy_impl(is_reference_predicate()) ;
}
{
if ( m_initialized )
destroy_impl(is_reference_predicate()) ;
}
unspecified_bool_type safe_bool() const { return m_initialized ? &this_type::is_initialized : 0 ; }
@ -410,7 +375,7 @@ class optional : public optional_detail::optional_base<T>
typedef BOOST_DEDUCED_TYPENAME base::unspecified_bool_type unspecified_bool_type ;
public :
typedef optional<T> this_type ;
typedef BOOST_DEDUCED_TYPENAME base::value_type value_type ;
@ -426,13 +391,13 @@ class optional : public optional_detail::optional_base<T>
// Creates an optional<T> uninitialized.
// No-throw
optional( none_t const& none_ ) : base(none_) {}
optional( detail::none_t const& none_ ) : base(none_) {}
// Creates an optional<T> initialized with 'val'.
// Can throw if T::T(T const&) does
optional ( argument_type val ) : base(val) {}
#ifndef BOOST_OPTIONAL_NO_CONVERTING_COPY_CTOR
// NOTE: MSVC needs templated versions first
@ -466,7 +431,7 @@ class optional : public optional_detail::optional_base<T>
// Creates a deep copy of another optional<T>
// Can throw if T::T(T const&) does
optional ( optional const& rhs ) : base(rhs) {}
// No-throw (assuming T::~T() doesn't)
~optional() {}
@ -488,7 +453,14 @@ class optional : public optional_detail::optional_base<T>
template<class U>
optional& operator= ( optional<U> const& rhs )
{
this->assign(rhs.get());
this->destroy(); // no-throw
if ( rhs.is_initialized() )
{
// An exception can be thrown here.
// It it happens, THIS will be left uninitialized.
this->assign(rhs.get());
}
return *this ;
}
#endif
@ -513,7 +485,7 @@ class optional : public optional_detail::optional_base<T>
// Assigns from a "none"
// Which destroys the current value, if any, leaving this UNINITIALIZED
// No-throw (assuming T::~T() doesn't)
optional& operator= ( none_t const& none_ )
optional& operator= ( detail::none_t const& none_ )
{
this->assign( none_ ) ;
return *this ;
@ -635,62 +607,62 @@ bool operator >= ( optional<T> const& x, optional<T> const& y )
template<class T>
inline
bool operator == ( optional<T> const& x, none_t const& )
bool operator == ( optional<T> const& x, detail::none_t const& )
{ return equal_pointees(x, optional<T>() ); }
template<class T>
inline
bool operator < ( optional<T> const& x, none_t const& )
bool operator < ( optional<T> const& x, detail::none_t const& )
{ return less_pointees(x,optional<T>() ); }
template<class T>
inline
bool operator != ( optional<T> const& x, none_t const& y )
bool operator != ( optional<T> const& x, detail::none_t const& y )
{ return !( x == y ) ; }
template<class T>
inline
bool operator > ( optional<T> const& x, none_t const& y )
bool operator > ( optional<T> const& x, detail::none_t const& y )
{ return y < x ; }
template<class T>
inline
bool operator <= ( optional<T> const& x, none_t const& y )
bool operator <= ( optional<T> const& x, detail::none_t const& y )
{ return !( y < x ) ; }
template<class T>
inline
bool operator >= ( optional<T> const& x, none_t const& y )
bool operator >= ( optional<T> const& x, detail::none_t const& y )
{ return !( x < y ) ; }
template<class T>
inline
bool operator == ( none_t const& x, optional<T> const& y )
bool operator == ( detail::none_t const& x, optional<T> const& y )
{ return equal_pointees(optional<T>() ,y); }
template<class T>
inline
bool operator < ( none_t const& x, optional<T> const& y )
bool operator < ( detail::none_t const& x, optional<T> const& y )
{ return less_pointees(optional<T>() ,y); }
template<class T>
inline
bool operator != ( none_t const& x, optional<T> const& y )
bool operator != ( detail::none_t const& x, optional<T> const& y )
{ return !( x == y ) ; }
template<class T>
inline
bool operator > ( none_t const& x, optional<T> const& y )
bool operator > ( detail::none_t const& x, optional<T> const& y )
{ return y < x ; }
template<class T>
inline
bool operator <= ( none_t const& x, optional<T> const& y )
bool operator <= ( detail::none_t const& x, optional<T> const& y )
{ return !( y < x ) ; }
template<class T>
inline
bool operator >= ( none_t const& x, optional<T> const& y )
bool operator >= ( detail::none_t const& x, optional<T> const& y )
{ return !( x < y ) ; }
//
@ -707,9 +679,8 @@ namespace optional_detail {
#endif
// optional's swap:
// If both are initialized, calls swap(T&, T&). If this swap throws, both will remain initialized but their values are now unspecified.
// If only one is initialized, calls U.reset(*I), THEN I.reset().
// If U.reset(*I) throws, both are left UNCHANGED (U is kept uinitialized and I is never reset)
// If both are initialized, calls swap(T&, T&), with whatever exception guarantess are given there.
// If only one is initialized, calls I.reset() and U.reset(*I), with the Basic Guarantee
// If both are uninitialized, do nothing (no-throw)
template<class T>
inline
@ -717,12 +688,12 @@ void optional_swap ( optional<T>& x, optional<T>& y )
{
if ( !x && !!y )
{
x.reset(*y);
x.reset(*y); // Basic guarantee.
y.reset();
}
else if ( !!x && !y )
{
y.reset(*x);
y.reset(*x); // Basic guarantee.
x.reset();
}
else if ( !!x && !!y )