Chris@16
|
1 /*-----------------------------------------------------------------------------+
|
Chris@16
|
2 Copyright (c) 2009-2009: Joachim Faulhaber
|
Chris@16
|
3 +------------------------------------------------------------------------------+
|
Chris@16
|
4 Distributed under the Boost Software License, Version 1.0.
|
Chris@16
|
5 (See accompanying file LICENCE.txt or copy at
|
Chris@16
|
6 http://www.boost.org/LICENSE_1_0.txt)
|
Chris@16
|
7 +-----------------------------------------------------------------------------*/
|
Chris@16
|
8 #ifndef BOOST_ICL_DETAIL_MAPPED_REFERENCE_HPP_JOFA_091108
|
Chris@16
|
9 #define BOOST_ICL_DETAIL_MAPPED_REFERENCE_HPP_JOFA_091108
|
Chris@16
|
10
|
Chris@16
|
11 #include <boost/type_traits/is_const.hpp>
|
Chris@16
|
12 #include <boost/type_traits/remove_const.hpp>
|
Chris@16
|
13 #include <boost/mpl/if.hpp>
|
Chris@16
|
14 #include <boost/icl/type_traits/is_concept_equivalent.hpp>
|
Chris@16
|
15
|
Chris@16
|
16 namespace boost{namespace icl
|
Chris@16
|
17 {
|
Chris@16
|
18
|
Chris@16
|
19 template<class FirstT, class SecondT> class mapped_reference;
|
Chris@16
|
20
|
Chris@16
|
21 //------------------------------------------------------------------------------
|
Chris@16
|
22 template<class Type>
|
Chris@16
|
23 struct is_mapped_reference_combinable{
|
Chris@16
|
24 typedef is_mapped_reference_combinable type;
|
Chris@16
|
25 BOOST_STATIC_CONSTANT(bool, value = false);
|
Chris@16
|
26 };
|
Chris@16
|
27
|
Chris@16
|
28 template<class FirstT, class SecondT>
|
Chris@16
|
29 struct is_mapped_reference_combinable<std::pair<const FirstT,SecondT> >
|
Chris@16
|
30 {
|
Chris@16
|
31 typedef is_mapped_reference_combinable<std::pair<const FirstT,SecondT> > type;
|
Chris@16
|
32 BOOST_STATIC_CONSTANT(bool, value = true);
|
Chris@16
|
33 };
|
Chris@16
|
34
|
Chris@16
|
35 template<class FirstT, class SecondT>
|
Chris@16
|
36 struct is_mapped_reference_combinable<std::pair<FirstT,SecondT> >
|
Chris@16
|
37 {
|
Chris@16
|
38 typedef is_mapped_reference_combinable<std::pair<FirstT,SecondT> > type;
|
Chris@16
|
39 BOOST_STATIC_CONSTANT(bool, value = true);
|
Chris@16
|
40 };
|
Chris@16
|
41
|
Chris@16
|
42 //------------------------------------------------------------------------------
|
Chris@16
|
43 template<class Type>
|
Chris@16
|
44 struct is_mapped_reference_or_combinable{
|
Chris@16
|
45 typedef is_mapped_reference_or_combinable type;
|
Chris@16
|
46 BOOST_STATIC_CONSTANT(bool, value = is_mapped_reference_combinable<Type>::value);
|
Chris@16
|
47 };
|
Chris@16
|
48
|
Chris@16
|
49 template<class FirstT, class SecondT>
|
Chris@16
|
50 struct is_mapped_reference_or_combinable<mapped_reference<FirstT,SecondT> >
|
Chris@16
|
51 {
|
Chris@16
|
52 typedef is_mapped_reference_or_combinable<mapped_reference<FirstT,SecondT> > type;
|
Chris@16
|
53 BOOST_STATIC_CONSTANT(bool, value = true);
|
Chris@16
|
54 };
|
Chris@16
|
55
|
Chris@16
|
56
|
Chris@16
|
57
|
Chris@16
|
58 //------------------------------------------------------------------------------
|
Chris@16
|
59 template<class FirstT, class SecondT>
|
Chris@16
|
60 class mapped_reference
|
Chris@16
|
61 {
|
Chris@16
|
62 private:
|
Chris@16
|
63 mapped_reference& operator = (const mapped_reference&);
|
Chris@16
|
64 public:
|
Chris@16
|
65 typedef FirstT first_type;
|
Chris@16
|
66 typedef SecondT second_type;
|
Chris@16
|
67 typedef mapped_reference type;
|
Chris@16
|
68
|
Chris@16
|
69 typedef typename
|
Chris@16
|
70 mpl::if_<is_const<second_type>,
|
Chris@16
|
71 second_type&,
|
Chris@16
|
72 const second_type&>::type second_reference_type;
|
Chris@16
|
73
|
Chris@16
|
74 typedef std::pair< first_type, second_type> std_pair_type;
|
Chris@16
|
75 typedef std::pair<const first_type, second_type> key_std_pair_type;
|
Chris@16
|
76
|
Chris@16
|
77 const first_type& first ;
|
Chris@16
|
78 second_reference_type second;
|
Chris@16
|
79
|
Chris@16
|
80 mapped_reference(const FirstT& fst, second_reference_type snd) : first(fst), second(snd){}
|
Chris@16
|
81
|
Chris@16
|
82 template<class FstT, class SndT>
|
Chris@16
|
83 mapped_reference(const mapped_reference<FstT, SndT>& source):
|
Chris@16
|
84 first(source.first), second(source.second){}
|
Chris@16
|
85
|
Chris@16
|
86 template<class FstT, class SndT>
|
Chris@16
|
87 operator std::pair<FstT,SndT>(){ return std::pair<FstT,SndT>(first, second); }
|
Chris@16
|
88
|
Chris@16
|
89 template<class Comparand>
|
Chris@16
|
90 typename enable_if<is_mapped_reference_or_combinable<Comparand>, bool>::type
|
Chris@16
|
91 operator == (const Comparand& right)const
|
Chris@16
|
92 { return first == right.first && second == right.second; }
|
Chris@16
|
93
|
Chris@16
|
94 template<class Comparand>
|
Chris@16
|
95 typename enable_if<is_mapped_reference_or_combinable<Comparand>, bool>::type
|
Chris@16
|
96 operator != (const Comparand& right)const
|
Chris@16
|
97 { return !(*this == right); }
|
Chris@16
|
98
|
Chris@16
|
99 template<class Comparand>
|
Chris@16
|
100 typename enable_if<is_mapped_reference_or_combinable<Comparand>, bool>::type
|
Chris@16
|
101 operator < (const Comparand& right)const
|
Chris@16
|
102 {
|
Chris@16
|
103 return first < right.first
|
Chris@16
|
104 ||(!(right.first < first) && second < right.second);
|
Chris@16
|
105 }
|
Chris@16
|
106
|
Chris@16
|
107 template<class Comparand>
|
Chris@16
|
108 typename enable_if<is_mapped_reference_or_combinable<Comparand>, bool>::type
|
Chris@16
|
109 operator > (const Comparand& right)const
|
Chris@16
|
110 {
|
Chris@16
|
111 return first > right.first
|
Chris@16
|
112 ||(!(right.first > first) && second > right.second);
|
Chris@16
|
113 }
|
Chris@16
|
114
|
Chris@16
|
115 template<class Comparand>
|
Chris@16
|
116 typename enable_if<is_mapped_reference_or_combinable<Comparand>, bool>::type
|
Chris@16
|
117 operator <= (const Comparand& right)const
|
Chris@16
|
118 {
|
Chris@16
|
119 return !(*this > right);
|
Chris@16
|
120 }
|
Chris@16
|
121
|
Chris@16
|
122 template<class Comparand>
|
Chris@16
|
123 typename enable_if<is_mapped_reference_or_combinable<Comparand>, bool>::type
|
Chris@16
|
124 operator >= (const Comparand& right)const
|
Chris@16
|
125 {
|
Chris@16
|
126 return !(*this < right);
|
Chris@16
|
127 }
|
Chris@16
|
128
|
Chris@16
|
129 };
|
Chris@16
|
130
|
Chris@16
|
131 //------------------------------------------------------------------------------
|
Chris@16
|
132 template<class FirstT, class SecondT, class StdPairT>
|
Chris@16
|
133 inline typename enable_if<is_mapped_reference_combinable<StdPairT>, bool>::type
|
Chris@16
|
134 operator == ( const StdPairT& left,
|
Chris@16
|
135 const mapped_reference<FirstT, SecondT>& right)
|
Chris@16
|
136 {
|
Chris@16
|
137 return right == left;
|
Chris@16
|
138 }
|
Chris@16
|
139
|
Chris@16
|
140 template<class FirstT, class SecondT, class StdPairT>
|
Chris@16
|
141 inline typename enable_if<is_mapped_reference_combinable<StdPairT>, bool>::type
|
Chris@16
|
142 operator != ( const StdPairT& left,
|
Chris@16
|
143 const mapped_reference<FirstT, SecondT>& right)
|
Chris@16
|
144 {
|
Chris@16
|
145 return !(right == left);
|
Chris@16
|
146 }
|
Chris@16
|
147
|
Chris@16
|
148 //------------------------------------------------------------------------------
|
Chris@16
|
149 template<class FirstT, class SecondT, class StdPairT>
|
Chris@16
|
150 inline typename enable_if<is_mapped_reference_combinable<StdPairT>, bool>::type
|
Chris@16
|
151 operator < ( const StdPairT& left,
|
Chris@16
|
152 const mapped_reference<FirstT, SecondT>& right)
|
Chris@16
|
153 {
|
Chris@16
|
154 return right > left;
|
Chris@16
|
155 }
|
Chris@16
|
156
|
Chris@16
|
157 //------------------------------------------------------------------------------
|
Chris@16
|
158 template<class FirstT, class SecondT, class StdPairT>
|
Chris@16
|
159 inline typename enable_if<is_mapped_reference_combinable<StdPairT>, bool>::type
|
Chris@16
|
160 operator > ( const StdPairT& left,
|
Chris@16
|
161 const mapped_reference<FirstT, SecondT>& right)
|
Chris@16
|
162 {
|
Chris@16
|
163 return right < left;
|
Chris@16
|
164 }
|
Chris@16
|
165
|
Chris@16
|
166 //------------------------------------------------------------------------------
|
Chris@16
|
167 template<class FirstT, class SecondT, class StdPairT>
|
Chris@16
|
168 inline typename enable_if<is_mapped_reference_combinable<StdPairT>, bool>::type
|
Chris@16
|
169 operator <= ( const StdPairT& left,
|
Chris@16
|
170 const mapped_reference<FirstT, SecondT>& right)
|
Chris@16
|
171 {
|
Chris@16
|
172 return !(right < left);
|
Chris@16
|
173 }
|
Chris@16
|
174
|
Chris@16
|
175 //------------------------------------------------------------------------------
|
Chris@16
|
176 template<class FirstT, class SecondT, class StdPairT>
|
Chris@16
|
177 inline typename enable_if<is_mapped_reference_combinable<StdPairT>, bool>::type
|
Chris@16
|
178 operator >= ( const StdPairT& left,
|
Chris@16
|
179 const mapped_reference<FirstT, SecondT>& right)
|
Chris@16
|
180 {
|
Chris@16
|
181 return !(left < right);
|
Chris@16
|
182 }
|
Chris@16
|
183
|
Chris@16
|
184 //------------------------------------------------------------------------------
|
Chris@16
|
185 //------------------------------------------------------------------------------
|
Chris@16
|
186 template<class FirstT, class SecondT>
|
Chris@16
|
187 inline mapped_reference<FirstT, SecondT> make_mapped_reference(const FirstT& left, SecondT& right)
|
Chris@16
|
188 { return mapped_reference<FirstT, SecondT>(left, right); }
|
Chris@16
|
189
|
Chris@16
|
190 }} // namespace icl boost
|
Chris@16
|
191
|
Chris@16
|
192 #endif // BOOST_ICL_DETAIL_MAPPED_REFERENCE_HPP_JOFA_091108
|