epoc32/include/stdapis/boost/multi_index/identity.hpp
branchSymbian3
changeset 4 837f303aceeb
equal deleted inserted replaced
3:e1b950c65cb4 4:837f303aceeb
       
     1 /* Copyright 2003-2006 Joaquín M López Muñoz.
       
     2  * Distributed under the Boost Software License, Version 1.0.
       
     3  * (See accompanying file LICENSE_1_0.txt or copy at
       
     4  * http://www.boost.org/LICENSE_1_0.txt)
       
     5  *
       
     6  * See http://www.boost.org/libs/multi_index for library home page.
       
     7  */
       
     8 
       
     9 #ifndef BOOST_MULTI_INDEX_IDENTITY_HPP
       
    10 #define BOOST_MULTI_INDEX_IDENTITY_HPP
       
    11 
       
    12 #if defined(_MSC_VER)&&(_MSC_VER>=1200)
       
    13 #pragma once
       
    14 #endif
       
    15 
       
    16 #include <boost/config.hpp>
       
    17 #include <boost/mpl/if.hpp>
       
    18 #include <boost/multi_index/identity_fwd.hpp>
       
    19 #include <boost/type_traits/is_const.hpp>
       
    20 #include <boost/type_traits/remove_const.hpp>
       
    21 #include <boost/utility/enable_if.hpp>
       
    22 
       
    23 #if !defined(BOOST_NO_SFINAE)
       
    24 #include <boost/type_traits/is_convertible.hpp>
       
    25 #endif
       
    26 
       
    27 namespace boost{
       
    28 
       
    29 template<class Type> class reference_wrapper; /* fwd decl. */
       
    30 
       
    31 namespace multi_index{
       
    32 
       
    33 namespace detail{
       
    34 
       
    35 /* identity is a do-nothing key extractor that returns the [const] Type&
       
    36  * object passed.
       
    37  * Additionally, identity is overloaded to support referece_wrappers
       
    38  * of Type and "chained pointers" to Type's. By chained pointer to Type we
       
    39  * mean a  type  P such that, given a p of type P
       
    40  *   *...n...*x is convertible to Type&, for some n>=1.
       
    41  * Examples of chained pointers are raw and smart pointers, iterators and
       
    42  * arbitrary combinations of these (vg. Type** or auto_ptr<Type*>.)
       
    43  */
       
    44 
       
    45 /* NB. Some overloads of operator() have an extra dummy parameter int=0.
       
    46  * This disambiguator serves several purposes:
       
    47  *  - Without it, MSVC++ 6.0 incorrectly regards some overloads as
       
    48  *    specializations of a previous member function template.
       
    49  *  - MSVC++ 6.0/7.0 seem to incorrectly treat some different memfuns
       
    50  *    as if they have the same signature.
       
    51  *  - If remove_const is broken due to lack of PTS, int=0 avoids the
       
    52  *    declaration of memfuns with identical signature.
       
    53  */
       
    54 
       
    55 template<typename Type>
       
    56 struct const_identity_base
       
    57 {
       
    58   typedef Type result_type;
       
    59 
       
    60   template<typename ChainedPtr>
       
    61 
       
    62 #if !defined(BOOST_NO_SFINAE)
       
    63   typename disable_if<is_convertible<const ChainedPtr&,Type&>,Type&>::type
       
    64 #else
       
    65   Type&
       
    66 #endif 
       
    67   
       
    68   operator()(const ChainedPtr& x)const
       
    69   {
       
    70     return operator()(*x);
       
    71   }
       
    72 
       
    73   Type& operator()(Type& x)const
       
    74   {
       
    75     return x;
       
    76   }
       
    77 
       
    78   Type& operator()(const reference_wrapper<Type>& x)const
       
    79   { 
       
    80     return x.get();
       
    81   }
       
    82 
       
    83   Type& operator()(
       
    84     const reference_wrapper<typename remove_const<Type>::type>& x,int=0)const
       
    85   { 
       
    86     return x.get();
       
    87   }
       
    88 };
       
    89 
       
    90 template<typename Type>
       
    91 struct non_const_identity_base
       
    92 {
       
    93   typedef Type result_type;
       
    94 
       
    95   /* templatized for pointer-like types */
       
    96   
       
    97   template<typename ChainedPtr>
       
    98 
       
    99 #if !defined(BOOST_NO_SFINAE)
       
   100   typename disable_if<
       
   101     is_convertible<const ChainedPtr&,const Type&>,Type&>::type
       
   102 #else
       
   103   Type&
       
   104 #endif 
       
   105     
       
   106   operator()(const ChainedPtr& x)const
       
   107   {
       
   108     return operator()(*x);
       
   109   }
       
   110 
       
   111   const Type& operator()(const Type& x,int=0)const
       
   112   {
       
   113     return x;
       
   114   }
       
   115 
       
   116   Type& operator()(Type& x)const
       
   117   {
       
   118     return x;
       
   119   }
       
   120 
       
   121   const Type& operator()(const reference_wrapper<const Type>& x,int=0)const
       
   122   { 
       
   123     return x.get();
       
   124   }
       
   125 
       
   126   Type& operator()(const reference_wrapper<Type>& x)const
       
   127   { 
       
   128     return x.get();
       
   129   }
       
   130 };
       
   131 
       
   132 } /* namespace multi_index::detail */
       
   133 
       
   134 template<class Type>
       
   135 struct identity:
       
   136   mpl::if_c<
       
   137     is_const<Type>::value,
       
   138     detail::const_identity_base<Type>,detail::non_const_identity_base<Type>
       
   139   >::type
       
   140 {
       
   141 };
       
   142 
       
   143 } /* namespace multi_index */
       
   144 
       
   145 } /* namespace boost */
       
   146 
       
   147 #endif