Chris@16
|
1
|
Chris@16
|
2 // Copyright (C) 2005-2011 Daniel James
|
Chris@16
|
3 // Distributed under the Boost Software License, Version 1.0. (See accompanying
|
Chris@16
|
4 // file LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt)
|
Chris@16
|
5
|
Chris@16
|
6 #ifndef BOOST_UNORDERED_DETAIL_EXTRACT_KEY_HPP_INCLUDED
|
Chris@16
|
7 #define BOOST_UNORDERED_DETAIL_EXTRACT_KEY_HPP_INCLUDED
|
Chris@16
|
8
|
Chris@101
|
9 #include <boost/config.hpp>
|
Chris@101
|
10 #if defined(BOOST_HAS_PRAGMA_ONCE)
|
Chris@101
|
11 #pragma once
|
Chris@101
|
12 #endif
|
Chris@101
|
13
|
Chris@16
|
14 #include <boost/unordered/detail/table.hpp>
|
Chris@16
|
15
|
Chris@16
|
16 namespace boost {
|
Chris@16
|
17 namespace unordered {
|
Chris@16
|
18 namespace detail {
|
Chris@16
|
19
|
Chris@16
|
20 // key extractors
|
Chris@16
|
21 //
|
Chris@16
|
22 // no throw
|
Chris@16
|
23 //
|
Chris@16
|
24 // 'extract_key' is called with the emplace parameters to return a
|
Chris@16
|
25 // key if available or 'no_key' is one isn't and will need to be
|
Chris@16
|
26 // constructed. This could be done by overloading the emplace implementation
|
Chris@16
|
27 // for the different cases, but that's a bit tricky on compilers without
|
Chris@16
|
28 // variadic templates.
|
Chris@16
|
29
|
Chris@16
|
30 struct no_key {
|
Chris@16
|
31 no_key() {}
|
Chris@16
|
32 template <class T> no_key(T const&) {}
|
Chris@16
|
33 };
|
Chris@16
|
34
|
Chris@16
|
35 template <typename Key, typename T>
|
Chris@16
|
36 struct is_key {
|
Chris@16
|
37 template <typename T2>
|
Chris@16
|
38 static choice1::type test(T2 const&);
|
Chris@16
|
39 static choice2::type test(Key const&);
|
Chris@16
|
40
|
Chris@16
|
41 enum { value = sizeof(test(boost::unordered::detail::make<T>())) ==
|
Chris@16
|
42 sizeof(choice2::type) };
|
Chris@16
|
43
|
Chris@16
|
44 typedef typename boost::detail::if_true<value>::
|
Chris@16
|
45 BOOST_NESTED_TEMPLATE then<Key const&, no_key>::type type;
|
Chris@16
|
46 };
|
Chris@16
|
47
|
Chris@16
|
48 template <class ValueType>
|
Chris@16
|
49 struct set_extractor
|
Chris@16
|
50 {
|
Chris@16
|
51 typedef ValueType value_type;
|
Chris@16
|
52 typedef ValueType key_type;
|
Chris@16
|
53
|
Chris@16
|
54 static key_type const& extract(key_type const& v)
|
Chris@16
|
55 {
|
Chris@16
|
56 return v;
|
Chris@16
|
57 }
|
Chris@16
|
58
|
Chris@16
|
59 static no_key extract()
|
Chris@16
|
60 {
|
Chris@16
|
61 return no_key();
|
Chris@16
|
62 }
|
Chris@16
|
63
|
Chris@16
|
64 template <class Arg>
|
Chris@16
|
65 static no_key extract(Arg const&)
|
Chris@16
|
66 {
|
Chris@16
|
67 return no_key();
|
Chris@16
|
68 }
|
Chris@16
|
69
|
Chris@16
|
70 #if !defined(BOOST_NO_CXX11_VARIADIC_TEMPLATES)
|
Chris@16
|
71 template <class Arg1, class Arg2, class... Args>
|
Chris@16
|
72 static no_key extract(Arg1 const&, Arg2 const&, Args const&...)
|
Chris@16
|
73 {
|
Chris@16
|
74 return no_key();
|
Chris@16
|
75 }
|
Chris@16
|
76 #else
|
Chris@16
|
77 template <class Arg1, class Arg2>
|
Chris@16
|
78 static no_key extract(Arg1 const&, Arg2 const&)
|
Chris@16
|
79 {
|
Chris@16
|
80 return no_key();
|
Chris@16
|
81 }
|
Chris@16
|
82 #endif
|
Chris@16
|
83 };
|
Chris@16
|
84
|
Chris@16
|
85 template <class Key, class ValueType>
|
Chris@16
|
86 struct map_extractor
|
Chris@16
|
87 {
|
Chris@16
|
88 typedef ValueType value_type;
|
Chris@16
|
89 typedef typename boost::remove_const<Key>::type key_type;
|
Chris@16
|
90
|
Chris@16
|
91 static key_type const& extract(value_type const& v)
|
Chris@16
|
92 {
|
Chris@16
|
93 return v.first;
|
Chris@16
|
94 }
|
Chris@16
|
95
|
Chris@16
|
96 template <class Second>
|
Chris@16
|
97 static key_type const& extract(std::pair<key_type, Second> const& v)
|
Chris@16
|
98 {
|
Chris@16
|
99 return v.first;
|
Chris@16
|
100 }
|
Chris@16
|
101
|
Chris@16
|
102 template <class Second>
|
Chris@16
|
103 static key_type const& extract(
|
Chris@16
|
104 std::pair<key_type const, Second> const& v)
|
Chris@16
|
105 {
|
Chris@16
|
106 return v.first;
|
Chris@16
|
107 }
|
Chris@16
|
108
|
Chris@16
|
109 template <class Arg1>
|
Chris@16
|
110 static key_type const& extract(key_type const& k, Arg1 const&)
|
Chris@16
|
111 {
|
Chris@16
|
112 return k;
|
Chris@16
|
113 }
|
Chris@16
|
114
|
Chris@16
|
115 static no_key extract()
|
Chris@16
|
116 {
|
Chris@16
|
117 return no_key();
|
Chris@16
|
118 }
|
Chris@16
|
119
|
Chris@16
|
120 template <class Arg>
|
Chris@16
|
121 static no_key extract(Arg const&)
|
Chris@16
|
122 {
|
Chris@16
|
123 return no_key();
|
Chris@16
|
124 }
|
Chris@16
|
125
|
Chris@16
|
126 template <class Arg1, class Arg2>
|
Chris@16
|
127 static no_key extract(Arg1 const&, Arg2 const&)
|
Chris@16
|
128 {
|
Chris@16
|
129 return no_key();
|
Chris@16
|
130 }
|
Chris@16
|
131
|
Chris@16
|
132 #if !defined(BOOST_NO_CXX11_VARIADIC_TEMPLATES)
|
Chris@16
|
133 template <class Arg1, class Arg2, class Arg3, class... Args>
|
Chris@16
|
134 static no_key extract(Arg1 const&, Arg2 const&, Arg3 const&,
|
Chris@16
|
135 Args const&...)
|
Chris@16
|
136 {
|
Chris@16
|
137 return no_key();
|
Chris@16
|
138 }
|
Chris@16
|
139 #endif
|
Chris@16
|
140
|
Chris@16
|
141 #if !defined(BOOST_NO_CXX11_VARIADIC_TEMPLATES)
|
Chris@16
|
142
|
Chris@16
|
143 #define BOOST_UNORDERED_KEY_FROM_TUPLE(namespace_) \
|
Chris@16
|
144 template <typename T2> \
|
Chris@16
|
145 static no_key extract(boost::unordered::piecewise_construct_t, \
|
Chris@16
|
146 namespace_ tuple<> const&, T2 const&) \
|
Chris@16
|
147 { \
|
Chris@16
|
148 return no_key(); \
|
Chris@16
|
149 } \
|
Chris@16
|
150 \
|
Chris@16
|
151 template <typename T, typename T2> \
|
Chris@16
|
152 static typename is_key<key_type, T>::type \
|
Chris@16
|
153 extract(boost::unordered::piecewise_construct_t, \
|
Chris@16
|
154 namespace_ tuple<T> const& k, T2 const&) \
|
Chris@16
|
155 { \
|
Chris@16
|
156 return typename is_key<key_type, T>::type( \
|
Chris@16
|
157 namespace_ get<0>(k)); \
|
Chris@16
|
158 }
|
Chris@16
|
159
|
Chris@16
|
160 #else
|
Chris@16
|
161
|
Chris@16
|
162 #define BOOST_UNORDERED_KEY_FROM_TUPLE(namespace_) \
|
Chris@16
|
163 static no_key extract(boost::unordered::piecewise_construct_t, \
|
Chris@16
|
164 namespace_ tuple<> const&) \
|
Chris@16
|
165 { \
|
Chris@16
|
166 return no_key(); \
|
Chris@16
|
167 } \
|
Chris@16
|
168 \
|
Chris@16
|
169 template <typename T> \
|
Chris@16
|
170 static typename is_key<key_type, T>::type \
|
Chris@16
|
171 extract(boost::unordered::piecewise_construct_t, \
|
Chris@16
|
172 namespace_ tuple<T> const& k) \
|
Chris@16
|
173 { \
|
Chris@16
|
174 return typename is_key<key_type, T>::type( \
|
Chris@16
|
175 namespace_ get<0>(k)); \
|
Chris@16
|
176 }
|
Chris@16
|
177
|
Chris@16
|
178 #endif
|
Chris@16
|
179
|
Chris@16
|
180 BOOST_UNORDERED_KEY_FROM_TUPLE(boost::)
|
Chris@16
|
181
|
Chris@16
|
182 #if !defined(BOOST_NO_CXX11_HDR_TUPLE)
|
Chris@16
|
183 BOOST_UNORDERED_KEY_FROM_TUPLE(std::)
|
Chris@16
|
184 #endif
|
Chris@16
|
185 };
|
Chris@16
|
186 }}}
|
Chris@16
|
187
|
Chris@16
|
188 #endif
|