159 lines
3.4 KiB
C++
159 lines
3.4 KiB
C++
//////////////////////////////////////////////////////////////////////////////
|
|
//
|
|
// (C) Copyright Ion Gaztanaga 2012-2012.
|
|
// 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/move for documentation.
|
|
//
|
|
//////////////////////////////////////////////////////////////////////////////
|
|
|
|
//! \file
|
|
|
|
#ifndef BOOST_MOVE_DETAIL_META_UTILS_HPP
|
|
#define BOOST_MOVE_DETAIL_META_UTILS_HPP
|
|
|
|
#include <boost/move/detail/config_begin.hpp>
|
|
|
|
//Small meta-typetraits to support move
|
|
|
|
namespace boost {
|
|
namespace move_detail {
|
|
|
|
//if_
|
|
template<bool C, typename T1, typename T2>
|
|
struct if_c
|
|
{
|
|
typedef T1 type;
|
|
};
|
|
|
|
template<typename T1, typename T2>
|
|
struct if_c<false,T1,T2>
|
|
{
|
|
typedef T2 type;
|
|
};
|
|
|
|
template<typename T1, typename T2, typename T3>
|
|
struct if_
|
|
{
|
|
typedef typename if_c<0 != T1::value, T2, T3>::type type;
|
|
};
|
|
|
|
//enable_if_
|
|
template <bool B, class T = void>
|
|
struct enable_if_c
|
|
{
|
|
typedef T type;
|
|
};
|
|
|
|
template <class T>
|
|
struct enable_if_c<false, T> {};
|
|
|
|
template <class Cond, class T = void>
|
|
struct enable_if : public enable_if_c<Cond::value, T> {};
|
|
|
|
template <class Cond, class T = void>
|
|
struct disable_if : public enable_if_c<!Cond::value, T> {};
|
|
|
|
//integral_constant
|
|
template<class T, T v>
|
|
struct integral_constant
|
|
{
|
|
static const T value = v;
|
|
typedef T value_type;
|
|
typedef integral_constant<T, v> type;
|
|
};
|
|
|
|
//identity
|
|
template <class T>
|
|
struct identity
|
|
{
|
|
typedef T type;
|
|
};
|
|
|
|
//is_convertible
|
|
template <class T, class U>
|
|
class is_convertible
|
|
{
|
|
typedef char true_t;
|
|
class false_t { char dummy[2]; };
|
|
static true_t dispatch(U);
|
|
static false_t dispatch(...);
|
|
static T &trigger();
|
|
public:
|
|
enum { value = sizeof(dispatch(trigger())) == sizeof(true_t) };
|
|
};
|
|
|
|
//and_ not_
|
|
template <typename Condition1, typename Condition2, typename Condition3 = integral_constant<bool, true> >
|
|
struct and_
|
|
: public integral_constant<bool, Condition1::value && Condition2::value && Condition3::value>
|
|
{};
|
|
|
|
template <typename Boolean>
|
|
struct not_
|
|
: public integral_constant<bool, !Boolean::value>
|
|
{};
|
|
|
|
//is_lvalue_reference
|
|
template<class T>
|
|
struct is_lvalue_reference
|
|
: public integral_constant<bool, false>
|
|
{};
|
|
|
|
template<class T>
|
|
struct is_lvalue_reference<T&>
|
|
: public integral_constant<bool, true>
|
|
{};
|
|
|
|
template<class T>
|
|
struct is_class_or_union
|
|
{
|
|
struct twochar { char _[2]; };
|
|
template <class U>
|
|
static char is_class_or_union_tester(void(U::*)(void));
|
|
template <class U>
|
|
static twochar is_class_or_union_tester(...);
|
|
static const bool value = sizeof(is_class_or_union_tester<T>(0)) == sizeof(char);
|
|
};
|
|
|
|
struct empty{};
|
|
|
|
//addressof
|
|
template<class T> struct addr_impl_ref
|
|
{
|
|
T & v_;
|
|
inline addr_impl_ref( T & v ): v_( v ) {}
|
|
inline operator T& () const { return v_; }
|
|
|
|
private:
|
|
addr_impl_ref & operator=(const addr_impl_ref &);
|
|
};
|
|
|
|
template<class T> struct addressof_impl
|
|
{
|
|
static inline T * f( T & v, long )
|
|
{
|
|
return reinterpret_cast<T*>(
|
|
&const_cast<char&>(reinterpret_cast<const volatile char &>(v)));
|
|
}
|
|
|
|
static inline T * f( T * v, int )
|
|
{ return v; }
|
|
};
|
|
|
|
template<class T>
|
|
inline T * addressof( T & v )
|
|
{
|
|
return ::boost::move_detail::addressof_impl<T>::f
|
|
( ::boost::move_detail::addr_impl_ref<T>( v ), 0 );
|
|
}
|
|
|
|
} //namespace move_detail {
|
|
} //namespace boost {
|
|
|
|
#include <boost/move/detail/config_end.hpp>
|
|
|
|
#endif //#ifndef BOOST_MOVE_DETAIL_META_UTILS_HPP
|