epoc32/include/stdapis/boost/multi_index/mem_fun.hpp
author William Roberts <williamr@symbian.org>
Wed, 31 Mar 2010 12:33:34 +0100
branchSymbian3
changeset 4 837f303aceeb
permissions -rw-r--r--
Current Symbian^3 public API header files (from PDK 3.0.h)
This is the epoc32/include tree with the "platform" subtrees removed, and
all but a selected few mbg and rsg files removed.
williamr@2
     1
/* Copyright 2003-2006 Joaquín M López Muñoz.
williamr@2
     2
 * Distributed under the Boost Software License, Version 1.0.
williamr@2
     3
 * (See accompanying file LICENSE_1_0.txt or copy at
williamr@2
     4
 * http://www.boost.org/LICENSE_1_0.txt)
williamr@2
     5
 *
williamr@2
     6
 * See http://www.boost.org/libs/multi_index for library home page.
williamr@2
     7
 */
williamr@2
     8
williamr@2
     9
#ifndef BOOST_MULTI_INDEX_MEM_FUN_HPP
williamr@2
    10
#define BOOST_MULTI_INDEX_MEM_FUN_HPP
williamr@2
    11
williamr@2
    12
#if defined(_MSC_VER)&&(_MSC_VER>=1200)
williamr@2
    13
#pragma once
williamr@2
    14
#endif
williamr@2
    15
williamr@2
    16
#include <boost/config.hpp> /* keep it first to prevent nasty warns in MSVC */
williamr@2
    17
#include <boost/mpl/if.hpp>
williamr@2
    18
#include <boost/type_traits/remove_reference.hpp>
williamr@2
    19
#include <boost/utility/enable_if.hpp>
williamr@2
    20
williamr@2
    21
#if !defined(BOOST_NO_SFINAE)
williamr@2
    22
#include <boost/type_traits/is_convertible.hpp>
williamr@2
    23
#endif
williamr@2
    24
williamr@2
    25
namespace boost{
williamr@2
    26
williamr@2
    27
template<class T> class reference_wrapper; /* fwd decl. */
williamr@2
    28
williamr@2
    29
namespace multi_index{
williamr@2
    30
williamr@2
    31
/* mem_fun implements a read-only key extractor based on a given non-const
williamr@2
    32
 * member function of a class.
williamr@2
    33
 * const_mem_fun does the same for const member functions.
williamr@2
    34
 * Additionally, mem_fun  and const_mem_fun are overloaded to support
williamr@2
    35
 * referece_wrappers of T and "chained pointers" to T's. By chained pointer
williamr@2
    36
 * to T we  mean a type P such that, given a p of Type P
williamr@2
    37
 *   *...n...*x is convertible to T&, for some n>=1.
williamr@2
    38
 * Examples of chained pointers are raw and smart pointers, iterators and
williamr@2
    39
 * arbitrary combinations of these (vg. T** or auto_ptr<T*>.)
williamr@2
    40
 */
williamr@2
    41
williamr@2
    42
/* NB. Some overloads of operator() have an extra dummy parameter int=0.
williamr@2
    43
 * This disambiguator serves several purposes:
williamr@2
    44
 *  - Without it, MSVC++ 6.0 incorrectly regards some overloads as
williamr@2
    45
 *    specializations of a previous member function template.
williamr@2
    46
 *  - MSVC++ 6.0/7.0 seem to incorrectly treat some different memfuns
williamr@2
    47
 *    as if they have the same signature.
williamr@2
    48
 *  - If remove_const is broken due to lack of PTS, int=0 avoids the
williamr@2
    49
 *    declaration of memfuns with identical signature.
williamr@2
    50
 */
williamr@2
    51
williamr@2
    52
template<class Class,typename Type,Type (Class::*PtrToMemberFunction)()const>
williamr@2
    53
struct const_mem_fun
williamr@2
    54
{
williamr@2
    55
  typedef typename remove_reference<Type>::type result_type;
williamr@2
    56
williamr@2
    57
  template<typename ChainedPtr>
williamr@2
    58
williamr@2
    59
#if !defined(BOOST_NO_SFINAE)
williamr@2
    60
  typename disable_if<
williamr@2
    61
    is_convertible<const ChainedPtr&,const Class&>,Type>::type
williamr@2
    62
#else
williamr@2
    63
  Type
williamr@2
    64
#endif
williamr@2
    65
williamr@2
    66
  operator()(const ChainedPtr& x)const
williamr@2
    67
  {
williamr@2
    68
    return operator()(*x);
williamr@2
    69
  }
williamr@2
    70
williamr@2
    71
  Type operator()(const Class& x)const
williamr@2
    72
  {
williamr@2
    73
    return (x.*PtrToMemberFunction)();
williamr@2
    74
  }
williamr@2
    75
williamr@2
    76
  Type operator()(const reference_wrapper<const Class>& x)const
williamr@2
    77
  { 
williamr@2
    78
    return operator()(x.get());
williamr@2
    79
  }
williamr@2
    80
williamr@2
    81
  Type operator()(const reference_wrapper<Class>& x,int=0)const
williamr@2
    82
  { 
williamr@2
    83
    return operator()(x.get());
williamr@2
    84
  }
williamr@2
    85
};
williamr@2
    86
williamr@2
    87
template<class Class,typename Type,Type (Class::*PtrToMemberFunction)()>
williamr@2
    88
struct mem_fun
williamr@2
    89
{
williamr@2
    90
  typedef typename remove_reference<Type>::type result_type;
williamr@2
    91
williamr@2
    92
  template<typename ChainedPtr>
williamr@2
    93
williamr@2
    94
#if !defined(BOOST_NO_SFINAE)
williamr@2
    95
  typename disable_if<
williamr@2
    96
    is_convertible<ChainedPtr&,Class&>,Type>::type
williamr@2
    97
#else
williamr@2
    98
  Type
williamr@2
    99
#endif
williamr@2
   100
williamr@2
   101
  operator()(const ChainedPtr& x)const
williamr@2
   102
  {
williamr@2
   103
    return operator()(*x);
williamr@2
   104
  }
williamr@2
   105
williamr@2
   106
  Type operator()(Class& x)const
williamr@2
   107
  {
williamr@2
   108
    return (x.*PtrToMemberFunction)();
williamr@2
   109
  }
williamr@2
   110
williamr@2
   111
  Type operator()(const reference_wrapper<Class>& x)const
williamr@2
   112
  { 
williamr@2
   113
    return operator()(x.get());
williamr@2
   114
  }
williamr@2
   115
};
williamr@2
   116
williamr@2
   117
/* MSVC++ 6.0 has problems with const member functions as non-type template
williamr@2
   118
 * parameters, somehow it takes them as non-const. mem_fun_explicit workarounds
williamr@2
   119
 * this defficiency by accepting an extra type parameter that specifies the
williamr@2
   120
 * signature of he member function. The workaround was found at:
williamr@2
   121
 *   Daniel, C.:"Re: weird typedef problem in VC",
williamr@2
   122
 *   news:microsoft.public.vc.language, 21st nov 2002, 
williamr@2
   123
 *   http://groups.google.com/groups?
williamr@2
   124
 *     hl=en&lr=&ie=UTF-8&selm=ukwvg3O0BHA.1512%40tkmsftngp05
williamr@2
   125
 */
williamr@2
   126
williamr@2
   127
template<
williamr@2
   128
  class Class,typename Type,
williamr@2
   129
  typename PtrToMemberFunctionType,PtrToMemberFunctionType PtrToMemberFunction>
williamr@2
   130
struct const_mem_fun_explicit
williamr@2
   131
{
williamr@2
   132
  typedef typename remove_reference<Type>::type result_type;
williamr@2
   133
williamr@2
   134
  template<typename ChainedPtr>
williamr@2
   135
williamr@2
   136
#if !defined(BOOST_NO_SFINAE)
williamr@2
   137
  typename disable_if<
williamr@2
   138
    is_convertible<const ChainedPtr&,const Class&>,Type>::type
williamr@2
   139
#else
williamr@2
   140
  Type
williamr@2
   141
#endif
williamr@2
   142
williamr@2
   143
  operator()(const ChainedPtr& x)const
williamr@2
   144
  {
williamr@2
   145
    return operator()(*x);
williamr@2
   146
  }
williamr@2
   147
williamr@2
   148
  Type operator()(const Class& x)const
williamr@2
   149
  {
williamr@2
   150
    return (x.*PtrToMemberFunction)();
williamr@2
   151
  }
williamr@2
   152
williamr@2
   153
  Type operator()(const reference_wrapper<const Class>& x)const
williamr@2
   154
  { 
williamr@2
   155
    return operator()(x.get());
williamr@2
   156
  }
williamr@2
   157
williamr@2
   158
  Type operator()(const reference_wrapper<Class>& x,int=0)const
williamr@2
   159
  { 
williamr@2
   160
    return operator()(x.get());
williamr@2
   161
  }
williamr@2
   162
};
williamr@2
   163
williamr@2
   164
template<
williamr@2
   165
  class Class,typename Type,
williamr@2
   166
  typename PtrToMemberFunctionType,PtrToMemberFunctionType PtrToMemberFunction>
williamr@2
   167
struct mem_fun_explicit
williamr@2
   168
{
williamr@2
   169
  typedef typename remove_reference<Type>::type result_type;
williamr@2
   170
williamr@2
   171
  template<typename ChainedPtr>
williamr@2
   172
williamr@2
   173
#if !defined(BOOST_NO_SFINAE)
williamr@2
   174
  typename disable_if<
williamr@2
   175
    is_convertible<ChainedPtr&,Class&>,Type>::type
williamr@2
   176
#else
williamr@2
   177
  Type
williamr@2
   178
#endif
williamr@2
   179
williamr@2
   180
  operator()(const ChainedPtr& x)const
williamr@2
   181
  {
williamr@2
   182
    return operator()(*x);
williamr@2
   183
  }
williamr@2
   184
williamr@2
   185
  Type operator()(Class& x)const
williamr@2
   186
  {
williamr@2
   187
    return (x.*PtrToMemberFunction)();
williamr@2
   188
  }
williamr@2
   189
williamr@2
   190
  Type operator()(const reference_wrapper<Class>& x)const
williamr@2
   191
  { 
williamr@2
   192
    return operator()(x.get());
williamr@2
   193
  }
williamr@2
   194
};
williamr@2
   195
williamr@2
   196
/* BOOST_MULTI_INDEX_CONST_MEM_FUN and BOOST_MULTI_INDEX_MEM_FUN resolve to
williamr@2
   197
 * mem_fun_explicit for MSVC++ 6.0 and to [const_]mem_fun otherwise.
williamr@2
   198
 */
williamr@2
   199
williamr@2
   200
#if defined(BOOST_MSVC)&&(BOOST_MSVC<1300)
williamr@2
   201
williamr@2
   202
#define BOOST_MULTI_INDEX_CONST_MEM_FUN(Class,Type,MemberFunName) \
williamr@2
   203
::boost::multi_index::const_mem_fun_explicit<\
williamr@2
   204
  Class,Type,Type (Class::*)()const,&Class::MemberFunName >
williamr@2
   205
#define BOOST_MULTI_INDEX_MEM_FUN(Class,Type,MemberFunName) \
williamr@2
   206
::boost::multi_index::mem_fun_explicit<\
williamr@2
   207
  Class,Type,Type (Class::*)(),&Class::MemberFunName >
williamr@2
   208
williamr@2
   209
#else
williamr@2
   210
williamr@2
   211
#define BOOST_MULTI_INDEX_CONST_MEM_FUN(Class,Type,MemberFunName) \
williamr@2
   212
::boost::multi_index::const_mem_fun< Class,Type,&Class::MemberFunName >
williamr@2
   213
#define BOOST_MULTI_INDEX_MEM_FUN(Class,Type,MemberFunName) \
williamr@2
   214
::boost::multi_index::mem_fun< Class,Type,&Class::MemberFunName >
williamr@2
   215
williamr@2
   216
#endif
williamr@2
   217
williamr@2
   218
} /* namespace multi_index */
williamr@2
   219
williamr@2
   220
} /* namespace boost */
williamr@2
   221
williamr@2
   222
#endif