forked from boostorg/intrusive
pack_options is now public, documented and tested so that it can be used by other libraries like Container, to specify new options for customizable containers.
This commit is contained in:
@@ -53,7 +53,9 @@ doxygen autodoc
|
||||
\"avltree_impl=avltree\" \\
|
||||
\"treap_set_impl=treap_set\" \\
|
||||
\"treap_multiset_impl=treap_multiset\" \\
|
||||
\"treap_impl=treap\""
|
||||
\"treap_impl=treap\" \\
|
||||
\"BOOST_INTRUSIVE_OPTION_CONSTANT(OPTION_NAME, TYPE, VALUE, CONSTANT_NAME) = template<TYPE VALUE> struct OPTION_NAME{};\" \\
|
||||
\"BOOST_INTRUSIVE_OPTION_TYPE(OPTION_NAME, TYPE, TYPEDEF_EXPR, TYPEDEF_NAME) = template<class TYPE> struct OPTION_NAME{};\" "
|
||||
;
|
||||
|
||||
xml intrusive : intrusive.qbk
|
||||
|
@@ -24,7 +24,8 @@ class MyClass : public auto_unlink_hook
|
||||
|
||||
public:
|
||||
MyClass(int i = 0) : int_(i) {}
|
||||
void unlink() { auto_unlink_hook::unlink(); }
|
||||
int get_int() { return int_; }
|
||||
void unlink() { auto_unlink_hook::unlink(); }
|
||||
bool is_linked() { return auto_unlink_hook::is_linked(); }
|
||||
};
|
||||
|
||||
|
@@ -16,15 +16,15 @@
|
||||
#include <boost/intrusive/detail/config_begin.hpp>
|
||||
#include <boost/intrusive/intrusive_fwd.hpp>
|
||||
#include <boost/intrusive/link_mode.hpp>
|
||||
#include <boost/intrusive/pack_options.hpp>
|
||||
#include <boost/intrusive/detail/mpl.hpp>
|
||||
#include <boost/intrusive/detail/utilities.hpp>
|
||||
#include <boost/static_assert.hpp>
|
||||
|
||||
|
||||
namespace boost {
|
||||
namespace intrusive {
|
||||
|
||||
/// @cond
|
||||
#ifndef BOOST_INTRUSIVE_DOXYGEN_INVOKED
|
||||
|
||||
//typedef void default_tag;
|
||||
struct default_tag;
|
||||
@@ -34,8 +34,6 @@ namespace detail{
|
||||
|
||||
struct default_hook_tag{};
|
||||
|
||||
#ifndef BOOST_INTRUSIVE_DOXYGEN_INVOKED
|
||||
|
||||
#define BOOST_INTRUSIVE_DEFAULT_HOOK_MARKER_DEFINITION(BOOST_INTRUSIVE_DEFAULT_HOOK_MARKER) \
|
||||
struct BOOST_INTRUSIVE_DEFAULT_HOOK_MARKER : public default_hook_tag\
|
||||
{\
|
||||
@@ -50,14 +48,9 @@ BOOST_INTRUSIVE_DEFAULT_HOOK_MARKER_DEFINITION(default_rbtree_hook);
|
||||
BOOST_INTRUSIVE_DEFAULT_HOOK_MARKER_DEFINITION(default_hashtable_hook);
|
||||
BOOST_INTRUSIVE_DEFAULT_HOOK_MARKER_DEFINITION(default_avltree_hook);
|
||||
BOOST_INTRUSIVE_DEFAULT_HOOK_MARKER_DEFINITION(default_bstree_hook);
|
||||
//BOOST_INTRUSIVE_DEFAULT_HOOK_MARKER_DEFINITION(default_splaytree_hook);
|
||||
//BOOST_INTRUSIVE_DEFAULT_HOOK_MARKER_DEFINITION(default_sgtree_hook);
|
||||
//BOOST_INTRUSIVE_DEFAULT_HOOK_MARKER_DEFINITION(default_treap_hook);
|
||||
|
||||
#undef BOOST_INTRUSIVE_DEFAULT_HOOK_MARKER_DEFINITION
|
||||
|
||||
#endif //BOOST_INTRUSIVE_DOXYGEN_INVOKED
|
||||
|
||||
template <class ValueTraits>
|
||||
struct eval_value_traits
|
||||
{
|
||||
@@ -165,7 +158,7 @@ struct get_value_traits
|
||||
//...get it's internal value traits using
|
||||
//the provided T value type.
|
||||
, get_base_value_traits<T, supposed_value_traits>
|
||||
//...else use it's internal value traits tag
|
||||
//...else use its internal value traits tag
|
||||
//(member hooks and custom value traits are in this group)
|
||||
, detail::eval_if_c
|
||||
< internal_member_value_traits<supposed_value_traits>::value
|
||||
@@ -191,7 +184,7 @@ struct get_node_traits
|
||||
//...get it's internal value traits using
|
||||
//the provided T value type.
|
||||
, get_base_node_traits<supposed_value_traits>
|
||||
//...else use it's internal value traits tag
|
||||
//...else use its internal value traits tag
|
||||
//(member hooks and custom value traits are in this group)
|
||||
, detail::eval_if_c
|
||||
< internal_member_value_traits<supposed_value_traits>::value
|
||||
@@ -203,50 +196,20 @@ struct get_node_traits
|
||||
|
||||
} //namespace detail{
|
||||
|
||||
/// @endcond
|
||||
#endif //BOOST_INTRUSIVE_DOXYGEN_INVOKED
|
||||
|
||||
//!This option setter specifies if the intrusive
|
||||
//!container stores its size as a member to
|
||||
//!obtain constant-time size() member.
|
||||
template<bool Enabled>
|
||||
struct constant_time_size
|
||||
{
|
||||
/// @cond
|
||||
template<class Base>
|
||||
struct pack : Base
|
||||
{
|
||||
static const bool constant_time_size = Enabled;
|
||||
};
|
||||
/// @endcond
|
||||
};
|
||||
BOOST_INTRUSIVE_OPTION_CONSTANT(constant_time_size, bool, Enabled, constant_time_size)
|
||||
|
||||
//!This option setter specifies the type that
|
||||
//!the container will use to store its size.
|
||||
template<class SizeType>
|
||||
struct size_type
|
||||
{
|
||||
/// @cond
|
||||
template<class Base>
|
||||
struct pack : Base
|
||||
{
|
||||
typedef SizeType size_type;
|
||||
};
|
||||
/// @endcond
|
||||
};
|
||||
BOOST_INTRUSIVE_OPTION_TYPE(size_type, SizeType, SizeType, size_type)
|
||||
|
||||
//!This option setter specifies the strict weak ordering
|
||||
//!comparison functor for the value type
|
||||
template<class Compare>
|
||||
struct compare
|
||||
{
|
||||
/// @cond
|
||||
template<class Base>
|
||||
struct pack : Base
|
||||
{
|
||||
typedef Compare compare;
|
||||
};
|
||||
/// @endcond
|
||||
};
|
||||
BOOST_INTRUSIVE_OPTION_TYPE(compare, Compare, Compare, compare)
|
||||
|
||||
//!This option setter for scapegoat containers specifies if
|
||||
//!the intrusive scapegoat container should use a non-variable
|
||||
@@ -260,74 +223,39 @@ struct compare
|
||||
//!If the user only needs an alpha value near 1/sqrt(2), this
|
||||
//!option also improves performance since avoids logarithm
|
||||
//!and division operations when rebalancing the tree.
|
||||
template<bool Enabled>
|
||||
struct floating_point
|
||||
{
|
||||
/// @cond
|
||||
template<class Base>
|
||||
struct pack : Base
|
||||
{
|
||||
static const bool floating_point = Enabled;
|
||||
};
|
||||
/// @endcond
|
||||
};
|
||||
BOOST_INTRUSIVE_OPTION_CONSTANT(floating_point, bool, Enabled, floating_point)
|
||||
|
||||
//!This option setter specifies the equality
|
||||
//!functor for the value type
|
||||
template<class Equal>
|
||||
struct equal
|
||||
{
|
||||
/// @cond
|
||||
template<class Base>
|
||||
struct pack : Base
|
||||
{
|
||||
typedef Equal equal;
|
||||
};
|
||||
/// @endcond
|
||||
};
|
||||
BOOST_INTRUSIVE_OPTION_TYPE(equal, Equal, Equal, equal)
|
||||
|
||||
//!This option setter specifies the equality
|
||||
//!functor for the value type
|
||||
template<class Priority>
|
||||
struct priority
|
||||
{
|
||||
/// @cond
|
||||
template<class Base>
|
||||
struct pack : Base
|
||||
{
|
||||
typedef Priority priority;
|
||||
};
|
||||
/// @endcond
|
||||
};
|
||||
BOOST_INTRUSIVE_OPTION_TYPE(priority, Priority, Priority, priority)
|
||||
|
||||
//!This option setter specifies the hash
|
||||
//!functor for the value type
|
||||
template<class Hash>
|
||||
struct hash
|
||||
{
|
||||
/// @cond
|
||||
template<class Base>
|
||||
struct pack : Base
|
||||
{
|
||||
typedef Hash hash;
|
||||
};
|
||||
/// @endcond
|
||||
};
|
||||
BOOST_INTRUSIVE_OPTION_TYPE(hash, Hash, Hash, hash)
|
||||
|
||||
//!This option setter specifies the relationship between the type
|
||||
//!to be managed by the container (the value type) and the node to be
|
||||
//!used in the node algorithms. It also specifies the linking policy.
|
||||
template<typename ValueTraits>
|
||||
struct value_traits
|
||||
{
|
||||
/// @cond
|
||||
template<class Base>
|
||||
struct pack : Base
|
||||
{
|
||||
typedef ValueTraits proto_value_traits;
|
||||
};
|
||||
/// @endcond
|
||||
};
|
||||
BOOST_INTRUSIVE_OPTION_TYPE(value_traits, ValueTraits, ValueTraits, proto_value_traits)
|
||||
|
||||
//#define BOOST_INTRUSIVE_COMMA ,
|
||||
//#define BOOST_INTRUSIVE_LESS <
|
||||
//#define BOOST_INTRUSIVE_MORE >
|
||||
//BOOST_INTRUSIVE_OPTION_TYPE (member_hook, Parent BOOST_INTRUSIVE_COMMA class MemberHook BOOST_INTRUSIVE_COMMA MemberHook Parent::* PtrToMember , mhtraits BOOST_INTRUSIVE_LESS Parent BOOST_INTRUSIVE_COMMA MemberHook BOOST_INTRUSIVE_COMMA PtrToMember BOOST_INTRUSIVE_MORE , proto_value_traits)
|
||||
//template< class Parent , class MemberHook , MemberHook Parent::* PtrToMember>
|
||||
//struct member_hook {
|
||||
// template<class Base> struct pack : Base {
|
||||
// typedef mhtraits < Parent , MemberHook , PtrToMember > proto_value_traits;
|
||||
// };
|
||||
//};
|
||||
//
|
||||
//#undef BOOST_INTRUSIVE_COMMA
|
||||
//#undef BOOST_INTRUSIVE_LESS
|
||||
//#undef BOOST_INTRUSIVE_MORE
|
||||
|
||||
//!This option setter specifies the member hook the
|
||||
//!container must use.
|
||||
@@ -336,27 +264,21 @@ template< typename Parent
|
||||
, MemberHook Parent::* PtrToMember>
|
||||
struct member_hook
|
||||
{
|
||||
/// @cond
|
||||
/*
|
||||
typedef typename MemberHook::hooktags::node_traits node_traits;
|
||||
typedef typename node_traits::node node_type;
|
||||
typedef node_type Parent::* Ptr2MemNode;
|
||||
typedef mhtraits
|
||||
< Parent
|
||||
, node_traits
|
||||
//This cast is really ugly but necessary to reduce template bloat.
|
||||
//Since we control the layout between the hook and the node, and there is
|
||||
//always single inheritance, the offset of the node is exactly the offset of
|
||||
//the hook. Since the node type is shared between all member hooks, this saves
|
||||
//quite a lot of symbol stuff.
|
||||
, (Ptr2MemNode)PtrToMember
|
||||
, MemberHook::hooktags::link_mode> member_value_traits;
|
||||
*/
|
||||
typedef mhtraits
|
||||
< Parent
|
||||
, MemberHook
|
||||
, PtrToMember
|
||||
> member_value_traits;
|
||||
// @cond
|
||||
// typedef typename MemberHook::hooktags::node_traits node_traits;
|
||||
// typedef typename node_traits::node node_type;
|
||||
// typedef node_type Parent::* Ptr2MemNode;
|
||||
// typedef mhtraits
|
||||
// < Parent
|
||||
// , node_traits
|
||||
// //This cast is really ugly but necessary to reduce template bloat.
|
||||
// //Since we control the layout between the hook and the node, and there is
|
||||
// //always single inheritance, the offset of the node is exactly the offset of
|
||||
// //the hook. Since the node type is shared between all member hooks, this saves
|
||||
// //quite a lot of symbol stuff.
|
||||
// , (Ptr2MemNode)PtrToMember
|
||||
// , MemberHook::hooktags::link_mode> member_value_traits;
|
||||
typedef mhtraits <Parent, MemberHook, PtrToMember> member_value_traits;
|
||||
template<class Base>
|
||||
struct pack : Base
|
||||
{
|
||||
@@ -365,158 +287,54 @@ struct member_hook
|
||||
/// @endcond
|
||||
};
|
||||
|
||||
|
||||
//!This option setter specifies the function object that will
|
||||
//!be used to convert between values to be inserted in a container
|
||||
//!and the hook to be used for that purpose.
|
||||
template< typename Functor>
|
||||
struct function_hook
|
||||
{
|
||||
/// @cond
|
||||
typedef fhtraits
|
||||
<Functor> function_value_traits;
|
||||
template<class Base>
|
||||
struct pack : Base
|
||||
{
|
||||
typedef function_value_traits proto_value_traits;
|
||||
};
|
||||
/// @endcond
|
||||
};
|
||||
|
||||
BOOST_INTRUSIVE_OPTION_TYPE(function_hook, Functor, fhtraits<Functor>, proto_value_traits)
|
||||
|
||||
//!This option setter specifies that the container
|
||||
//!must use the specified base hook
|
||||
template<typename BaseHook>
|
||||
struct base_hook
|
||||
{
|
||||
/// @cond
|
||||
template<class Base>
|
||||
struct pack : Base
|
||||
{
|
||||
typedef BaseHook proto_value_traits;
|
||||
};
|
||||
/// @endcond
|
||||
};
|
||||
BOOST_INTRUSIVE_OPTION_TYPE(base_hook, BaseHook, BaseHook, proto_value_traits)
|
||||
|
||||
//!This option setter specifies the type of
|
||||
//!a void pointer. This will instruct the hook
|
||||
//!to use this type of pointer instead of the
|
||||
//!default one
|
||||
template<class VoidPointer>
|
||||
struct void_pointer
|
||||
{
|
||||
/// @cond
|
||||
template<class Base>
|
||||
struct pack : Base
|
||||
{
|
||||
typedef VoidPointer void_pointer;
|
||||
};
|
||||
/// @endcond
|
||||
};
|
||||
BOOST_INTRUSIVE_OPTION_TYPE(void_pointer, VoidPointer, VoidPointer, void_pointer)
|
||||
|
||||
//!This option setter specifies the type of
|
||||
//!the tag of a base hook. A type cannot have two
|
||||
//!base hooks of the same type, so a tag can be used
|
||||
//!to differentiate two base hooks with otherwise same type
|
||||
template<class Tag>
|
||||
struct tag
|
||||
{
|
||||
/// @cond
|
||||
template<class Base>
|
||||
struct pack : Base
|
||||
{
|
||||
typedef Tag tag;
|
||||
};
|
||||
/// @endcond
|
||||
};
|
||||
BOOST_INTRUSIVE_OPTION_TYPE(tag, Tag, Tag, tag)
|
||||
|
||||
//!This option setter specifies the link mode
|
||||
//!(normal_link, safe_link or auto_unlink)
|
||||
template<link_mode_type LinkType>
|
||||
struct link_mode
|
||||
{
|
||||
/// @cond
|
||||
template<class Base>
|
||||
struct pack : Base
|
||||
{
|
||||
static const link_mode_type link_mode = LinkType;
|
||||
};
|
||||
/// @endcond
|
||||
};
|
||||
BOOST_INTRUSIVE_OPTION_CONSTANT(link_mode, link_mode_type, LinkType, link_mode)
|
||||
|
||||
//!This option setter specifies if the hook
|
||||
//!should be optimized for size instead of for speed.
|
||||
template<bool Enabled>
|
||||
struct optimize_size
|
||||
{
|
||||
/// @cond
|
||||
template<class Base>
|
||||
struct pack : Base
|
||||
{
|
||||
static const bool optimize_size = Enabled;
|
||||
};
|
||||
/// @endcond
|
||||
};
|
||||
BOOST_INTRUSIVE_OPTION_CONSTANT(optimize_size, bool, Enabled, optimize_size)
|
||||
|
||||
//!This option setter specifies if the list container should
|
||||
//!use a linear implementation instead of a circular one.
|
||||
template<bool Enabled>
|
||||
struct linear
|
||||
{
|
||||
/// @cond
|
||||
template<class Base>
|
||||
struct pack : Base
|
||||
{
|
||||
static const bool linear = Enabled;
|
||||
};
|
||||
/// @endcond
|
||||
};
|
||||
BOOST_INTRUSIVE_OPTION_CONSTANT(linear, bool, Enabled, linear)
|
||||
|
||||
//!This option setter specifies if the list container should
|
||||
//!use a linear implementation instead of a circular one.
|
||||
template<bool Enabled>
|
||||
struct cache_last
|
||||
{
|
||||
/// @cond
|
||||
template<class Base>
|
||||
struct pack : Base
|
||||
{
|
||||
static const bool cache_last = Enabled;
|
||||
};
|
||||
/// @endcond
|
||||
};
|
||||
BOOST_INTRUSIVE_OPTION_CONSTANT(cache_last, bool, Enabled, cache_last)
|
||||
|
||||
//!This option setter specifies the bucket traits
|
||||
//!class for unordered associative containers. When this option is specified,
|
||||
//!instead of using the default bucket traits, a user defined holder will be defined
|
||||
template<class BucketTraits>
|
||||
struct bucket_traits
|
||||
{
|
||||
/// @cond
|
||||
template<class Base>
|
||||
struct pack : Base
|
||||
{
|
||||
typedef BucketTraits bucket_traits;
|
||||
};
|
||||
/// @endcond
|
||||
};
|
||||
BOOST_INTRUSIVE_OPTION_TYPE(bucket_traits, BucketTraits, BucketTraits, bucket_traits)
|
||||
|
||||
//!This option setter specifies if the unordered hook
|
||||
//!should offer room to store the hash value.
|
||||
//!Storing the hash in the hook will speed up rehashing
|
||||
//!processes in applications where rehashing is frequent,
|
||||
//!rehashing might throw or the value is heavy to hash.
|
||||
template<bool Enabled>
|
||||
struct store_hash
|
||||
{
|
||||
/// @cond
|
||||
template<class Base>
|
||||
struct pack : Base
|
||||
{
|
||||
static const bool store_hash = Enabled;
|
||||
};
|
||||
/// @endcond
|
||||
};
|
||||
BOOST_INTRUSIVE_OPTION_CONSTANT(store_hash, bool, Enabled, store_hash)
|
||||
|
||||
//!This option setter specifies if the unordered hook
|
||||
//!should offer room to store another link to another node
|
||||
@@ -524,51 +342,20 @@ struct store_hash
|
||||
//!Storing this link will speed up lookups and insertions on
|
||||
//!unordered_multiset containers with a great number of elements
|
||||
//!with the same key.
|
||||
template<bool Enabled>
|
||||
struct optimize_multikey
|
||||
{
|
||||
/// @cond
|
||||
template<class Base>
|
||||
struct pack : Base
|
||||
{
|
||||
static const bool optimize_multikey = Enabled;
|
||||
};
|
||||
/// @endcond
|
||||
};
|
||||
BOOST_INTRUSIVE_OPTION_CONSTANT(optimize_multikey, bool, Enabled, optimize_multikey)
|
||||
|
||||
//!This option setter specifies if the bucket array will be always power of two.
|
||||
//!This allows using masks instead of the default modulo operation to determine
|
||||
//!the bucket number from the hash value, leading to better performance.
|
||||
//!In debug mode, if power of two buckets mode is activated, the bucket length
|
||||
//!will be checked to through assertions to assure the bucket length is power of two.
|
||||
template<bool Enabled>
|
||||
struct power_2_buckets
|
||||
{
|
||||
/// @cond
|
||||
template<class Base>
|
||||
struct pack : Base
|
||||
{
|
||||
static const bool power_2_buckets = Enabled;
|
||||
};
|
||||
/// @endcond
|
||||
};
|
||||
BOOST_INTRUSIVE_OPTION_CONSTANT(power_2_buckets, bool, Enabled, power_2_buckets)
|
||||
|
||||
//!This option setter specifies if the container will cache a pointer to the first
|
||||
//!non-empty bucket so that begin() is always constant-time.
|
||||
//!This is specially helpful when we can have containers with a few elements
|
||||
//!but with big bucket arrays (that is, hashtables with low load factors).
|
||||
template<bool Enabled>
|
||||
struct cache_begin
|
||||
{
|
||||
/// @cond
|
||||
template<class Base>
|
||||
struct pack : Base
|
||||
{
|
||||
static const bool cache_begin = Enabled;
|
||||
};
|
||||
/// @endcond
|
||||
};
|
||||
|
||||
BOOST_INTRUSIVE_OPTION_CONSTANT(cache_begin, bool, Enabled, cache_begin)
|
||||
|
||||
//!This option setter specifies if the container will compare the hash value
|
||||
//!before comparing objects. This option can't be specified if store_hash<>
|
||||
@@ -576,17 +363,7 @@ struct cache_begin
|
||||
//!This is specially helpful when we have containers with a high load factor.
|
||||
//!and the comparison function is much more expensive that comparing already
|
||||
//!stored hash values.
|
||||
template<bool Enabled>
|
||||
struct compare_hash
|
||||
{
|
||||
/// @cond
|
||||
template<class Base>
|
||||
struct pack : Base
|
||||
{
|
||||
static const bool compare_hash = Enabled;
|
||||
};
|
||||
/// @endcond
|
||||
};
|
||||
BOOST_INTRUSIVE_OPTION_CONSTANT(compare_hash, bool, Enabled, compare_hash)
|
||||
|
||||
//!This option setter specifies if the hash container will use incremental
|
||||
//!hashing. With incremental hashing the cost of hash table expansion is spread
|
||||
@@ -594,17 +371,7 @@ struct compare_hash
|
||||
//!Therefore linear hashing is well suited for interactive applications or real-time
|
||||
//!appplications where the worst-case insertion time of non-incremental hash containers
|
||||
//!(rehashing the whole bucket array) is not admisible.
|
||||
template<bool Enabled>
|
||||
struct incremental
|
||||
{
|
||||
/// @cond
|
||||
template<class Base>
|
||||
struct pack : Base
|
||||
{
|
||||
static const bool incremental = Enabled;
|
||||
};
|
||||
/// @endcond
|
||||
};
|
||||
BOOST_INTRUSIVE_OPTION_CONSTANT(incremental, bool, Enabled, incremental)
|
||||
|
||||
/// @cond
|
||||
|
||||
@@ -615,210 +382,6 @@ struct none
|
||||
{};
|
||||
};
|
||||
|
||||
//To-do: pass to variadic templates
|
||||
#if !defined(BOOST_INTRUSIVE_VARIADIC_TEMPLATES)
|
||||
|
||||
template<class Prev, class Next>
|
||||
struct do_pack
|
||||
{
|
||||
//Use "pack" member template to pack options
|
||||
typedef typename Next::template pack<Prev> type;
|
||||
};
|
||||
|
||||
template<class Prev>
|
||||
struct do_pack<Prev, void>
|
||||
{
|
||||
//Avoid packing "void" to shorten template names
|
||||
typedef Prev type;
|
||||
};
|
||||
|
||||
template
|
||||
< class DefaultOptions
|
||||
, class O1 = void
|
||||
, class O2 = void
|
||||
, class O3 = void
|
||||
, class O4 = void
|
||||
, class O5 = void
|
||||
, class O6 = void
|
||||
, class O7 = void
|
||||
, class O8 = void
|
||||
, class O9 = void
|
||||
, class O10 = void
|
||||
, class O11 = void
|
||||
>
|
||||
struct pack_options
|
||||
{
|
||||
// join options
|
||||
typedef
|
||||
typename do_pack
|
||||
< typename do_pack
|
||||
< typename do_pack
|
||||
< typename do_pack
|
||||
< typename do_pack
|
||||
< typename do_pack
|
||||
< typename do_pack
|
||||
< typename do_pack
|
||||
< typename do_pack
|
||||
< typename do_pack
|
||||
< typename do_pack
|
||||
< DefaultOptions
|
||||
, O1
|
||||
>::type
|
||||
, O2
|
||||
>::type
|
||||
, O3
|
||||
>::type
|
||||
, O4
|
||||
>::type
|
||||
, O5
|
||||
>::type
|
||||
, O6
|
||||
>::type
|
||||
, O7
|
||||
>::type
|
||||
, O8
|
||||
>::type
|
||||
, O9
|
||||
>::type
|
||||
, O10
|
||||
>::type
|
||||
, O11
|
||||
>::type
|
||||
type;
|
||||
};
|
||||
#else
|
||||
|
||||
//index_tuple
|
||||
template<int... Indexes>
|
||||
struct index_tuple{};
|
||||
|
||||
//build_number_seq
|
||||
template<std::size_t Num, typename Tuple = index_tuple<> >
|
||||
struct build_number_seq;
|
||||
|
||||
template<std::size_t Num, int... Indexes>
|
||||
struct build_number_seq<Num, index_tuple<Indexes...> >
|
||||
: build_number_seq<Num - 1, index_tuple<Indexes..., sizeof...(Indexes)> >
|
||||
{};
|
||||
|
||||
template<int... Indexes>
|
||||
struct build_number_seq<0, index_tuple<Indexes...> >
|
||||
{ typedef index_tuple<Indexes...> type; };
|
||||
|
||||
template<class ...Types>
|
||||
struct typelist
|
||||
{};
|
||||
|
||||
//invert_typelist
|
||||
template<class T>
|
||||
struct invert_typelist;
|
||||
|
||||
template<int I, typename Tuple>
|
||||
struct typelist_element;
|
||||
|
||||
template<int I, typename Head, typename... Tail>
|
||||
struct typelist_element<I, typelist<Head, Tail...> >
|
||||
{
|
||||
typedef typename typelist_element<I-1, typelist<Tail...> >::type type;
|
||||
};
|
||||
|
||||
template<typename Head, typename... Tail>
|
||||
struct typelist_element<0, typelist<Head, Tail...> >
|
||||
{
|
||||
typedef Head type;
|
||||
};
|
||||
|
||||
template<int ...Ints, class ...Types>
|
||||
typelist<typename typelist_element<(sizeof...(Types) - 1) - Ints, typelist<Types...> >::type...>
|
||||
inverted_typelist(index_tuple<Ints...>, typelist<Types...>)
|
||||
{
|
||||
return typelist<typename typelist_element<(sizeof...(Types) - 1) - Ints, typelist<Types...> >::type...>();
|
||||
}
|
||||
|
||||
//sizeof_typelist
|
||||
template<class Typelist>
|
||||
struct sizeof_typelist;
|
||||
|
||||
template<class ...Types>
|
||||
struct sizeof_typelist< typelist<Types...> >
|
||||
{
|
||||
static const std::size_t value = sizeof...(Types);
|
||||
};
|
||||
|
||||
//invert_typelist_impl
|
||||
template<class Typelist, class Indexes>
|
||||
struct invert_typelist_impl;
|
||||
|
||||
|
||||
template<class Typelist, int ...Ints>
|
||||
struct invert_typelist_impl< Typelist, index_tuple<Ints...> >
|
||||
{
|
||||
static const std::size_t last_idx = sizeof_typelist<Typelist>::value - 1;
|
||||
typedef typelist
|
||||
<typename typelist_element<last_idx - Ints, Typelist>::type...> type;
|
||||
};
|
||||
|
||||
template<class Typelist, int Int>
|
||||
struct invert_typelist_impl< Typelist, index_tuple<Int> >
|
||||
{
|
||||
typedef Typelist type;
|
||||
};
|
||||
|
||||
template<class Typelist>
|
||||
struct invert_typelist_impl< Typelist, index_tuple<> >
|
||||
{
|
||||
typedef Typelist type;
|
||||
};
|
||||
|
||||
//invert_typelist
|
||||
template<class Typelist>
|
||||
struct invert_typelist;
|
||||
|
||||
template<class ...Types>
|
||||
struct invert_typelist< typelist<Types...> >
|
||||
{
|
||||
typedef typelist<Types...> typelist_t;
|
||||
typedef typename build_number_seq<sizeof...(Types)>::type indexes_t;
|
||||
typedef typename invert_typelist_impl<typelist_t, indexes_t>::type type;
|
||||
};
|
||||
|
||||
//Do pack
|
||||
template<class Typelist>
|
||||
struct do_pack;
|
||||
|
||||
template<>
|
||||
struct do_pack<typelist<> >;
|
||||
|
||||
template<class Prev>
|
||||
struct do_pack<typelist<Prev> >
|
||||
{
|
||||
typedef Prev type;
|
||||
};
|
||||
|
||||
template<class Prev, class Last>
|
||||
struct do_pack<typelist<Prev, Last> >
|
||||
{
|
||||
typedef typename Prev::template pack<Last> type;
|
||||
};
|
||||
|
||||
template<class Prev, class ...Others>
|
||||
struct do_pack<typelist<Prev, Others...> >
|
||||
{
|
||||
typedef typename Prev::template pack
|
||||
<typename do_pack<typelist<Others...> >::type> type;
|
||||
};
|
||||
|
||||
|
||||
template<class ...Options>
|
||||
struct pack_options
|
||||
{
|
||||
typedef typelist<Options...> typelist_t;
|
||||
typedef typename invert_typelist<typelist_t>::type inverted_typelist;
|
||||
typedef typename do_pack<inverted_typelist>::type type;
|
||||
};
|
||||
|
||||
#endif
|
||||
|
||||
struct hook_defaults
|
||||
{
|
||||
typedef void* void_pointer;
|
||||
|
370
include/boost/intrusive/pack_options.hpp
Normal file
370
include/boost/intrusive/pack_options.hpp
Normal file
@@ -0,0 +1,370 @@
|
||||
/////////////////////////////////////////////////////////////////////////////
|
||||
//
|
||||
// (C) Copyright Ion Gaztanaga 2013-2013
|
||||
//
|
||||
// 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)
|
||||
//
|
||||
// See http://www.boost.org/libs/intrusive for documentation.
|
||||
//
|
||||
/////////////////////////////////////////////////////////////////////////////
|
||||
|
||||
#ifndef BOOST_INTRUSIVE_PACK_OPTIONS_HPP
|
||||
#define BOOST_INTRUSIVE_PACK_OPTIONS_HPP
|
||||
|
||||
#include <boost/intrusive/detail/config_begin.hpp>
|
||||
|
||||
namespace boost {
|
||||
namespace intrusive {
|
||||
|
||||
#ifndef BOOST_INTRUSIVE_DOXYGEN_INVOKED
|
||||
|
||||
#if !defined(BOOST_INTRUSIVE_VARIADIC_TEMPLATES)
|
||||
|
||||
template<class Prev, class Next>
|
||||
struct do_pack
|
||||
{
|
||||
//Use "pack" member template to pack options
|
||||
typedef typename Next::template pack<Prev> type;
|
||||
};
|
||||
|
||||
template<class Prev>
|
||||
struct do_pack<Prev, void>
|
||||
{
|
||||
//Avoid packing "void" to shorten template names
|
||||
typedef Prev type;
|
||||
};
|
||||
|
||||
template
|
||||
< class DefaultOptions
|
||||
, class O1 = void
|
||||
, class O2 = void
|
||||
, class O3 = void
|
||||
, class O4 = void
|
||||
, class O5 = void
|
||||
, class O6 = void
|
||||
, class O7 = void
|
||||
, class O8 = void
|
||||
, class O9 = void
|
||||
, class O10 = void
|
||||
, class O11 = void
|
||||
>
|
||||
struct pack_options
|
||||
{
|
||||
// join options
|
||||
typedef
|
||||
typename do_pack
|
||||
< typename do_pack
|
||||
< typename do_pack
|
||||
< typename do_pack
|
||||
< typename do_pack
|
||||
< typename do_pack
|
||||
< typename do_pack
|
||||
< typename do_pack
|
||||
< typename do_pack
|
||||
< typename do_pack
|
||||
< typename do_pack
|
||||
< DefaultOptions
|
||||
, O1
|
||||
>::type
|
||||
, O2
|
||||
>::type
|
||||
, O3
|
||||
>::type
|
||||
, O4
|
||||
>::type
|
||||
, O5
|
||||
>::type
|
||||
, O6
|
||||
>::type
|
||||
, O7
|
||||
>::type
|
||||
, O8
|
||||
>::type
|
||||
, O9
|
||||
>::type
|
||||
, O10
|
||||
>::type
|
||||
, O11
|
||||
>::type
|
||||
type;
|
||||
};
|
||||
#else
|
||||
|
||||
//index_tuple
|
||||
template<int... Indexes>
|
||||
struct index_tuple{};
|
||||
|
||||
//build_number_seq
|
||||
template<std::size_t Num, typename Tuple = index_tuple<> >
|
||||
struct build_number_seq;
|
||||
|
||||
template<std::size_t Num, int... Indexes>
|
||||
struct build_number_seq<Num, index_tuple<Indexes...> >
|
||||
: build_number_seq<Num - 1, index_tuple<Indexes..., sizeof...(Indexes)> >
|
||||
{};
|
||||
|
||||
template<int... Indexes>
|
||||
struct build_number_seq<0, index_tuple<Indexes...> >
|
||||
{ typedef index_tuple<Indexes...> type; };
|
||||
|
||||
template<class ...Types>
|
||||
struct typelist
|
||||
{};
|
||||
|
||||
//invert_typelist
|
||||
template<class T>
|
||||
struct invert_typelist;
|
||||
|
||||
template<int I, typename Tuple>
|
||||
struct typelist_element;
|
||||
|
||||
template<int I, typename Head, typename... Tail>
|
||||
struct typelist_element<I, typelist<Head, Tail...> >
|
||||
{
|
||||
typedef typename typelist_element<I-1, typelist<Tail...> >::type type;
|
||||
};
|
||||
|
||||
template<typename Head, typename... Tail>
|
||||
struct typelist_element<0, typelist<Head, Tail...> >
|
||||
{
|
||||
typedef Head type;
|
||||
};
|
||||
|
||||
template<int ...Ints, class ...Types>
|
||||
typelist<typename typelist_element<(sizeof...(Types) - 1) - Ints, typelist<Types...> >::type...>
|
||||
inverted_typelist(index_tuple<Ints...>, typelist<Types...>)
|
||||
{
|
||||
return typelist<typename typelist_element<(sizeof...(Types) - 1) - Ints, typelist<Types...> >::type...>();
|
||||
}
|
||||
|
||||
//sizeof_typelist
|
||||
template<class Typelist>
|
||||
struct sizeof_typelist;
|
||||
|
||||
template<class ...Types>
|
||||
struct sizeof_typelist< typelist<Types...> >
|
||||
{
|
||||
static const std::size_t value = sizeof...(Types);
|
||||
};
|
||||
|
||||
//invert_typelist_impl
|
||||
template<class Typelist, class Indexes>
|
||||
struct invert_typelist_impl;
|
||||
|
||||
|
||||
template<class Typelist, int ...Ints>
|
||||
struct invert_typelist_impl< Typelist, index_tuple<Ints...> >
|
||||
{
|
||||
static const std::size_t last_idx = sizeof_typelist<Typelist>::value - 1;
|
||||
typedef typelist
|
||||
<typename typelist_element<last_idx - Ints, Typelist>::type...> type;
|
||||
};
|
||||
|
||||
template<class Typelist, int Int>
|
||||
struct invert_typelist_impl< Typelist, index_tuple<Int> >
|
||||
{
|
||||
typedef Typelist type;
|
||||
};
|
||||
|
||||
template<class Typelist>
|
||||
struct invert_typelist_impl< Typelist, index_tuple<> >
|
||||
{
|
||||
typedef Typelist type;
|
||||
};
|
||||
|
||||
//invert_typelist
|
||||
template<class Typelist>
|
||||
struct invert_typelist;
|
||||
|
||||
template<class ...Types>
|
||||
struct invert_typelist< typelist<Types...> >
|
||||
{
|
||||
typedef typelist<Types...> typelist_t;
|
||||
typedef typename build_number_seq<sizeof...(Types)>::type indexes_t;
|
||||
typedef typename invert_typelist_impl<typelist_t, indexes_t>::type type;
|
||||
};
|
||||
|
||||
//Do pack
|
||||
template<class Typelist>
|
||||
struct do_pack;
|
||||
|
||||
template<>
|
||||
struct do_pack<typelist<> >;
|
||||
|
||||
template<class Prev>
|
||||
struct do_pack<typelist<Prev> >
|
||||
{
|
||||
typedef Prev type;
|
||||
};
|
||||
|
||||
template<class Prev, class Last>
|
||||
struct do_pack<typelist<Prev, Last> >
|
||||
{
|
||||
typedef typename Prev::template pack<Last> type;
|
||||
};
|
||||
|
||||
template<class Prev, class ...Others>
|
||||
struct do_pack<typelist<Prev, Others...> >
|
||||
{
|
||||
typedef typename Prev::template pack
|
||||
<typename do_pack<typelist<Others...> >::type> type;
|
||||
};
|
||||
|
||||
|
||||
template<class DefaultOptions, class ...Options>
|
||||
struct pack_options
|
||||
{
|
||||
typedef typelist<DefaultOptions, Options...> typelist_t;
|
||||
typedef typename invert_typelist<typelist_t>::type inverted_typelist;
|
||||
typedef typename do_pack<inverted_typelist>::type type;
|
||||
};
|
||||
|
||||
#endif //!defined(BOOST_INTRUSIVE_VARIADIC_TEMPLATES)
|
||||
|
||||
#define BOOST_INTRUSIVE_OPTION_TYPE(OPTION_NAME, TYPE, TYPEDEF_EXPR, TYPEDEF_NAME) \
|
||||
template< class TYPE> \
|
||||
struct OPTION_NAME \
|
||||
{ \
|
||||
template<class Base> \
|
||||
struct pack : Base \
|
||||
{ \
|
||||
typedef TYPEDEF_EXPR TYPEDEF_NAME; \
|
||||
}; \
|
||||
}; \
|
||||
//
|
||||
|
||||
#define BOOST_INTRUSIVE_OPTION_CONSTANT(OPTION_NAME, TYPE, VALUE, CONSTANT_NAME) \
|
||||
template< TYPE VALUE> \
|
||||
struct OPTION_NAME \
|
||||
{ \
|
||||
template<class Base> \
|
||||
struct pack : Base \
|
||||
{ \
|
||||
static const TYPE CONSTANT_NAME = VALUE; \
|
||||
}; \
|
||||
}; \
|
||||
//
|
||||
|
||||
#else //#ifndef BOOST_INTRUSIVE_DOXYGEN_INVOKED
|
||||
|
||||
//! This class is a utility that takes:
|
||||
//! - a default options class defining initial static constant
|
||||
//! and typedefs
|
||||
//! - several options defined with BOOST_INTRUSIVE_OPTION_CONSTANT and
|
||||
//! BOOST_INTRUSIVE_OPTION_TYPE
|
||||
//!
|
||||
//! and packs them together in a new type that defines all options as
|
||||
//! member typedefs or static constant values. Given options of form:
|
||||
//!
|
||||
//! \code
|
||||
//! BOOST_INTRUSIVE_OPTION_TYPE(my_pointer, VoidPointer, VoidPointer, my_pointer_type)
|
||||
//! BOOST_INTRUSIVE_OPTION_CONSTANT(incremental, bool, Enabled, is_incremental)
|
||||
//! \endcode
|
||||
//!
|
||||
//! the following expression
|
||||
//!
|
||||
//! \code
|
||||
//!
|
||||
//! struct default_options
|
||||
//! {
|
||||
//! typedef long int_type;
|
||||
//! static const int int_constant = -1;
|
||||
//! };
|
||||
//!
|
||||
//! pack_options< default_options, my_pointer<void*>, incremental<true> >::type
|
||||
//! \endcode
|
||||
//!
|
||||
//! will create a type that will contain the following typedefs/constants
|
||||
//!
|
||||
//! \code
|
||||
//! struct unspecified_type
|
||||
//! {
|
||||
//! //Default options
|
||||
//! typedef long int_type;
|
||||
//! static const int int_constant = -1;
|
||||
//!
|
||||
//! //Packed options (will ovewrite any default option)
|
||||
//! typedef void* my_pointer_type;
|
||||
//! static const bool is_incremental = true;
|
||||
//! };
|
||||
//! \endcode
|
||||
//!
|
||||
//! If an option is specified in the default options argument and later
|
||||
//! redefined as an option, the last definition will prevail.
|
||||
template<class DefaultOptions, class ...Options>
|
||||
struct pack_options
|
||||
{
|
||||
typedef unspecified_type type;
|
||||
};
|
||||
|
||||
//! Defines an option class of name OPTION_NAME that can be used to specify a type
|
||||
//! of type TYPE...
|
||||
//!
|
||||
//! \code
|
||||
//! struct OPTION_NAME<class TYPE>
|
||||
//! { /*unspecified_content*/ };
|
||||
//! \endcode
|
||||
//!
|
||||
//! ...that after being combined with
|
||||
//! <code>boost::intrusive::pack_options</code>,
|
||||
//! will typedef TYPE as a typedef of name TYPEDEF_NAME. Example:
|
||||
//!
|
||||
//! \code
|
||||
//! //[includes and namespaces omitted for brevity]
|
||||
//!
|
||||
//! //This macro will create the following class:
|
||||
//! // template<class VoidPointer>
|
||||
//! // struct my_pointer
|
||||
//! // { unspecified_content };
|
||||
//! BOOST_INTRUSIVE_OPTION_TYPE(my_pointer, VoidPointer, boost::remove_pointer<VoidPointer>::type, my_pointer_type)
|
||||
//!
|
||||
//! struct empty_default{};
|
||||
//!
|
||||
//! typedef pack_options< empty_default, typename my_pointer<void*> >::type::my_pointer_type type;
|
||||
//!
|
||||
//! BOOST_STATIC_ASSERT(( boost::is_same<type, void>::value ));
|
||||
//!
|
||||
//! \endcode
|
||||
#define BOOST_INTRUSIVE_OPTION_TYPE(OPTION_NAME, TYPE, TYPEDEF_EXPR, TYPEDEF_NAME)
|
||||
|
||||
//! Defines an option class of name OPTION_NAME that can be used to specify a constant
|
||||
//! of type TYPE with value VALUE...
|
||||
//!
|
||||
//! \code
|
||||
//! struct OPTION_NAME<TYPE VALUE>
|
||||
//! { /*unspecified_content*/ };
|
||||
//! \endcode
|
||||
//!
|
||||
//! ...that after being combined with
|
||||
//! <code>boost::intrusive::pack_options</code>,
|
||||
//! will contain a CONSTANT_NAME static constant of value VALUE. Example:
|
||||
//!
|
||||
//! \code
|
||||
//! //[includes and namespaces omitted for brevity]
|
||||
//!
|
||||
//! //This macro will create the following class:
|
||||
//! // template<bool Enabled>
|
||||
//! // struct incremental
|
||||
//! // { unspecified_content };
|
||||
//! BOOST_INTRUSIVE_OPTION_CONSTANT(incremental, bool, Enabled, is_incremental)
|
||||
//!
|
||||
//! struct empty_default{};
|
||||
//!
|
||||
//! const bool is_incremental = pack_options< empty_default, incremental<true> >::type::is_incremental;
|
||||
//!
|
||||
//! BOOST_STATIC_ASSERT(( is_incremental == true ));
|
||||
//!
|
||||
//! \endcode
|
||||
#define BOOST_INTRUSIVE_OPTION_CONSTANT(OPTION_NAME, TYPE, VALUE, CONSTANT_NAME)
|
||||
|
||||
#endif //#ifndef BOOST_INTRUSIVE_DOXYGEN_INVOKED
|
||||
|
||||
|
||||
} //namespace intrusive {
|
||||
} //namespace boost {
|
||||
|
||||
#include <boost/intrusive/detail/config_end.hpp>
|
||||
|
||||
#endif //#ifndef BOOST_INTRUSIVE_PACK_OPTIONS_HPP
|
@@ -115,6 +115,10 @@ Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "scary_iterators", "scary_it
|
||||
ProjectSection(ProjectDependencies) = postProject
|
||||
EndProjectSection
|
||||
EndProject
|
||||
Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "pack_options", "pack_options\pack_options.vcproj", "{77F4139B-281B-F694-7CB1-3495467B4D35}"
|
||||
ProjectSection(ProjectDependencies) = postProject
|
||||
EndProjectSection
|
||||
EndProject
|
||||
Global
|
||||
GlobalSection(SolutionConfiguration) = preSolution
|
||||
Debug = Debug
|
||||
@@ -239,6 +243,10 @@ Global
|
||||
{7679B41B-C1C5-FA34-9614-3547B3140346}.Debug.Build.0 = Debug|Win32
|
||||
{7679B41B-C1C5-FA34-9614-3547B3140346}.Release.ActiveCfg = Release|Win32
|
||||
{7679B41B-C1C5-FA34-9614-3547B3140346}.Release.Build.0 = Release|Win32
|
||||
{77F4139B-281B-F694-7CB1-3495467B4D35}.Debug.ActiveCfg = Debug|Win32
|
||||
{77F4139B-281B-F694-7CB1-3495467B4D35}.Debug.Build.0 = Debug|Win32
|
||||
{77F4139B-281B-F694-7CB1-3495467B4D35}.Release.ActiveCfg = Release|Win32
|
||||
{77F4139B-281B-F694-7CB1-3495467B4D35}.Release.Build.0 = Release|Win32
|
||||
EndGlobalSection
|
||||
GlobalSection(ExtensibilityGlobals) = postSolution
|
||||
EndGlobalSection
|
||||
|
@@ -157,6 +157,9 @@
|
||||
<File
|
||||
RelativePath="..\..\..\..\..\boost\intrusive\options.hpp">
|
||||
</File>
|
||||
<File
|
||||
RelativePath="..\..\..\..\..\boost\intrusive\pack_options.hpp">
|
||||
</File>
|
||||
<File
|
||||
RelativePath="..\..\..\..\..\boost\intrusive\parent_from_member.hpp">
|
||||
</File>
|
||||
|
133
proj/vc7ide/pack_options/pack_options.vcproj
Normal file
133
proj/vc7ide/pack_options/pack_options.vcproj
Normal file
@@ -0,0 +1,133 @@
|
||||
<?xml version="1.0" encoding="Windows-1252"?>
|
||||
<VisualStudioProject
|
||||
ProjectType="Visual C++"
|
||||
Version="7.10"
|
||||
Name="pack_options"
|
||||
ProjectGUID="{77F4139B-281B-F694-7CB1-3495467B4D35}"
|
||||
RootNamespace="pack_options"
|
||||
Keyword="Win32Proj">
|
||||
<Platforms>
|
||||
<Platform
|
||||
Name="Win32"/>
|
||||
</Platforms>
|
||||
<Configurations>
|
||||
<Configuration
|
||||
Name="Debug|Win32"
|
||||
OutputDirectory="Debug"
|
||||
IntermediateDirectory="Debug"
|
||||
ConfigurationType="1"
|
||||
CharacterSet="2">
|
||||
<Tool
|
||||
Name="VCCLCompilerTool"
|
||||
Optimization="0"
|
||||
AdditionalIncludeDirectories="../../../../../"
|
||||
PreprocessorDefinitions="BOOST_DATE_TIME_NO_LIB"
|
||||
GeneratePreprocessedFile="0"
|
||||
KeepComments="FALSE"
|
||||
MinimalRebuild="TRUE"
|
||||
BasicRuntimeChecks="3"
|
||||
RuntimeLibrary="5"
|
||||
DisableLanguageExtensions="FALSE"
|
||||
TreatWChar_tAsBuiltInType="TRUE"
|
||||
ForceConformanceInForLoopScope="TRUE"
|
||||
UsePrecompiledHeader="0"
|
||||
WarningLevel="4"
|
||||
Detect64BitPortabilityProblems="TRUE"
|
||||
DebugInformationFormat="4"/>
|
||||
<Tool
|
||||
Name="VCCustomBuildTool"/>
|
||||
<Tool
|
||||
Name="VCLinkerTool"
|
||||
OutputFile="$(OutDir)/pack_options.exe"
|
||||
LinkIncremental="2"
|
||||
GenerateDebugInformation="TRUE"
|
||||
ProgramDatabaseFile="$(OutDir)/pack_options.pdb"
|
||||
GenerateMapFile="TRUE"
|
||||
SubSystem="1"
|
||||
TargetMachine="1"/>
|
||||
<Tool
|
||||
Name="VCMIDLTool"/>
|
||||
<Tool
|
||||
Name="VCPostBuildEventTool"/>
|
||||
<Tool
|
||||
Name="VCPreBuildEventTool"/>
|
||||
<Tool
|
||||
Name="VCPreLinkEventTool"/>
|
||||
<Tool
|
||||
Name="VCResourceCompilerTool"/>
|
||||
<Tool
|
||||
Name="VCWebServiceProxyGeneratorTool"/>
|
||||
<Tool
|
||||
Name="VCXMLDataGeneratorTool"/>
|
||||
<Tool
|
||||
Name="VCWebDeploymentTool"/>
|
||||
<Tool
|
||||
Name="VCManagedWrapperGeneratorTool"/>
|
||||
<Tool
|
||||
Name="VCAuxiliaryManagedWrapperGeneratorTool"/>
|
||||
</Configuration>
|
||||
<Configuration
|
||||
Name="Release|Win32"
|
||||
OutputDirectory="Release"
|
||||
IntermediateDirectory="Release"
|
||||
ConfigurationType="1"
|
||||
CharacterSet="2">
|
||||
<Tool
|
||||
Name="VCCLCompilerTool"
|
||||
AdditionalIncludeDirectories="../../../../../"
|
||||
PreprocessorDefinitions="BOOST_DATE_TIME_NO_LIB"
|
||||
RuntimeLibrary="4"
|
||||
DisableLanguageExtensions="FALSE"
|
||||
ForceConformanceInForLoopScope="TRUE"
|
||||
UsePrecompiledHeader="0"
|
||||
WarningLevel="3"
|
||||
Detect64BitPortabilityProblems="TRUE"
|
||||
DebugInformationFormat="3"/>
|
||||
<Tool
|
||||
Name="VCCustomBuildTool"/>
|
||||
<Tool
|
||||
Name="VCLinkerTool"
|
||||
OutputFile="$(OutDir)/pack_options.exe"
|
||||
LinkIncremental="1"
|
||||
GenerateDebugInformation="TRUE"
|
||||
SubSystem="1"
|
||||
OptimizeReferences="2"
|
||||
EnableCOMDATFolding="2"
|
||||
TargetMachine="1"/>
|
||||
<Tool
|
||||
Name="VCMIDLTool"/>
|
||||
<Tool
|
||||
Name="VCPostBuildEventTool"/>
|
||||
<Tool
|
||||
Name="VCPreBuildEventTool"/>
|
||||
<Tool
|
||||
Name="VCPreLinkEventTool"/>
|
||||
<Tool
|
||||
Name="VCResourceCompilerTool"/>
|
||||
<Tool
|
||||
Name="VCWebServiceProxyGeneratorTool"/>
|
||||
<Tool
|
||||
Name="VCXMLDataGeneratorTool"/>
|
||||
<Tool
|
||||
Name="VCWebDeploymentTool"/>
|
||||
<Tool
|
||||
Name="VCManagedWrapperGeneratorTool"/>
|
||||
<Tool
|
||||
Name="VCAuxiliaryManagedWrapperGeneratorTool"/>
|
||||
</Configuration>
|
||||
</Configurations>
|
||||
<References>
|
||||
</References>
|
||||
<Files>
|
||||
<Filter
|
||||
Name="Source Files"
|
||||
Filter="cpp;c;cxx;def;odl;idl;hpj;bat;asm;asmx"
|
||||
UniqueIdentifier="{47FFA531-6474-B5A5-A661-272FA537F35F}">
|
||||
<File
|
||||
RelativePath="..\..\..\test\pack_options_test.cpp">
|
||||
</File>
|
||||
</Filter>
|
||||
</Files>
|
||||
<Globals>
|
||||
</Globals>
|
||||
</VisualStudioProject>
|
@@ -21,6 +21,7 @@
|
||||
Optimization="0"
|
||||
AdditionalIncludeDirectories="../../../../../"
|
||||
PreprocessorDefinitions="WIN32;_DEBUG;_CONSOLE"
|
||||
GeneratePreprocessedFile="0"
|
||||
MinimalRebuild="TRUE"
|
||||
BasicRuntimeChecks="3"
|
||||
RuntimeLibrary="5"
|
||||
|
60
test/pack_options_test.cpp
Normal file
60
test/pack_options_test.cpp
Normal file
@@ -0,0 +1,60 @@
|
||||
//////////////////////////////////////////////////////////////////////////////
|
||||
//
|
||||
// (C) Copyright Ion Gaztanaga 2013-2013. 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)
|
||||
//
|
||||
// See http://www.boost.org/libs/intrusive for documentation.
|
||||
//
|
||||
//////////////////////////////////////////////////////////////////////////////
|
||||
#include <boost/intrusive/detail/config_begin.hpp>
|
||||
#include <boost/type_traits/is_same.hpp>
|
||||
#include <boost/type_traits/remove_pointer.hpp>
|
||||
#include <boost/type_traits/add_pointer.hpp>
|
||||
#include <boost/static_assert.hpp>
|
||||
#include <boost/intrusive/pack_options.hpp>
|
||||
|
||||
struct empty_default{};
|
||||
|
||||
using namespace boost::intrusive;
|
||||
|
||||
//Test BOOST_INTRUSIVE_OPTION_CONSTANT
|
||||
BOOST_INTRUSIVE_OPTION_CONSTANT(incremental, bool, Enabled, is_incremental)
|
||||
const bool is_incremental_value = pack_options< empty_default, incremental<true> >::type::is_incremental;
|
||||
BOOST_STATIC_ASSERT(( is_incremental_value == true ));
|
||||
|
||||
//Test BOOST_INTRUSIVE_OPTION_TYPE
|
||||
BOOST_INTRUSIVE_OPTION_TYPE(my_pointer, VoidPointer, typename boost::remove_pointer<VoidPointer>::type, my_pointer_type)
|
||||
typedef pack_options< empty_default, my_pointer<void*> >::type::my_pointer_type my_pointer_type;
|
||||
BOOST_STATIC_ASSERT(( boost::is_same<my_pointer_type, void>::value ));
|
||||
|
||||
//test combination of BOOST_INTRUSIVE_OPTION_CONSTANT and BOOST_INTRUSIVE_OPTION_TYPE
|
||||
// First add new options
|
||||
struct default_options
|
||||
{
|
||||
static const long long_constant = -3;
|
||||
typedef double * double_typedef;
|
||||
};
|
||||
|
||||
BOOST_INTRUSIVE_OPTION_CONSTANT(incremental2, bool, Enabled, is_incremental2)
|
||||
BOOST_INTRUSIVE_OPTION_TYPE(my_pointer2, VoidPointer, typename boost::add_pointer<VoidPointer>::type, my_pointer_type2)
|
||||
typedef pack_options < default_options
|
||||
, incremental<false>
|
||||
, my_pointer<float*>
|
||||
, incremental2<true>
|
||||
, my_pointer2<const char*>
|
||||
>::type combined_type;
|
||||
BOOST_STATIC_ASSERT(( combined_type::is_incremental == false ));
|
||||
BOOST_STATIC_ASSERT(( combined_type::is_incremental2 == true ));
|
||||
BOOST_STATIC_ASSERT(( boost::is_same<combined_type::my_pointer_type, float >::value ));
|
||||
BOOST_STATIC_ASSERT(( boost::is_same<combined_type::my_pointer_type2, const char**>::value ));
|
||||
|
||||
//test packing the default options leads to a default options type
|
||||
BOOST_STATIC_ASSERT(( boost::is_same<pack_options<default_options>::type, default_options>::value ));
|
||||
|
||||
int main()
|
||||
{
|
||||
return 0;
|
||||
}
|
||||
|
||||
#include <boost/intrusive/detail/config_end.hpp>
|
Reference in New Issue
Block a user