libstdc++
types_traits.hpp
Go to the documentation of this file.
1 // -*- C++ -*-
2 
3 // Copyright (C) 2005, 2006, 2009, 2011 Free Software Foundation, Inc.
4 //
5 // This file is part of the GNU ISO C++ Library. This library is free
6 // software; you can redistribute it and/or modify it under the terms
7 // of the GNU General Public License as published by the Free Software
8 // Foundation; either version 3, or (at your option) any later
9 // version.
10 
11 // This library is distributed in the hope that it will be useful, but
12 // WITHOUT ANY WARRANTY; without even the implied warranty of
13 // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
14 // General Public License for more details.
15 
16 // Under Section 7 of GPL version 3, you are granted additional
17 // permissions described in the GCC Runtime Library Exception, version
18 // 3.1, as published by the Free Software Foundation.
19 
20 // You should have received a copy of the GNU General Public License and
21 // a copy of the GCC Runtime Library Exception along with this program;
22 // see the files COPYING3 and COPYING.RUNTIME respectively. If not, see
23 // <http://www.gnu.org/licenses/>.
24 
25 // Copyright (C) 2004 Ami Tavory and Vladimir Dreizin, IBM-HRL.
26 
27 // Permission to use, copy, modify, sell, and distribute this software
28 // is hereby granted without fee, provided that the above copyright
29 // notice appears in all copies, and that both that copyright notice
30 // and this permission notice appear in supporting documentation. None
31 // of the above authors, nor IBM Haifa Research Laboratories, make any
32 // representation about the suitability of this software for any
33 // purpose. It is provided "as is" without express or implied
34 // warranty.
35 
36 /**
37  * @file detail/types_traits.hpp
38  * Contains a traits class of types used by containers.
39  */
40 
41 #ifndef PB_DS_TYPES_TRAITS_HPP
42 #define PB_DS_TYPES_TRAITS_HPP
43 
44 #include <algorithm>
45 #include <utility>
48 #include <utility>
49 
50 namespace __gnu_pbds
51 {
52  namespace detail
53  {
54  /**
55  * @addtogroup traits Traits
56  * @{
57  */
58 
59  /// Primary template.
60  template<typename Key, typename Mapped>
62  {
63  static const bool __simple = is_simple<Key>::value
64  && is_simple<Mapped>::value;
65  typedef integral_constant<int, __simple> indicator;
66  };
67 
68  /// Specialization.
69  template<typename Key>
71  {
72  typedef integral_constant<int, is_simple<Key>::value> indicator;
73  };
74 
75 
76  /// Stored value.
77  template<typename _Tv>
78  struct stored_value
79  {
80  typedef _Tv value_type;
81  value_type m_value;
82  };
83 
84  /// Stored hash.
85  template<typename _Th>
86  struct stored_hash
87  {
88  typedef _Th hash_type;
89  hash_type m_hash;
90  };
91 
92  /// Primary template for representation of stored data.
93  /// Two types of data can be stored: value and hash.
94  template<typename _Tv, typename _Th>
95  struct stored_data
96  : public stored_value<_Tv>, public stored_hash<_Th>
97  { };
98 
99  /// Specialization for representation of stored data of just value type.
100  template<typename _Tv>
101  struct stored_data<_Tv, null_type>
102  : public stored_value<_Tv>
103  { };
104 
105  /// Primary template.
106  template<typename Key, typename Mapped, typename _Alloc, bool Store_Hash>
107  struct type_base;
108 
109  /**
110  * Specialization of type_base for the case where the hash value
111  * is not stored alongside each value.
112  */
113  template<typename Key, typename Mapped, typename _Alloc>
114  struct type_base<Key, Mapped, _Alloc, false>
115  {
116  public:
117  typedef typename _Alloc::size_type size_type;
118 
119  private:
120  typedef typename _Alloc::template rebind<Mapped> __rebind_m;
121  typedef typename __rebind_m::other __rebind_ma;
123  typedef typename _Alloc::template rebind<__value_type> __rebind_v;
124  typedef typename __rebind_v::other __rebind_va;
125 
126  public:
127  typedef typename __rebind_ma::value_type mapped_type;
128  typedef typename __rebind_ma::pointer mapped_pointer;
129  typedef typename __rebind_ma::const_pointer mapped_const_pointer;
130  typedef typename __rebind_ma::reference mapped_reference;
131  typedef typename __rebind_ma::const_reference mapped_const_reference;
132 
133  typedef typename __rebind_va::value_type value_type;
134  typedef typename __rebind_va::pointer pointer;
135  typedef typename __rebind_va::const_pointer const_pointer;
136  typedef typename __rebind_va::reference reference;
137  typedef typename __rebind_va::const_reference const_reference;
138 
140  };
141 
142  /**
143  * Specialization of type_base for the case where the hash value
144  * is stored alongside each value.
145  */
146  template<typename Key, typename Mapped, typename _Alloc>
147  struct type_base<Key, Mapped, _Alloc, true>
148  {
149  public:
150  typedef typename _Alloc::size_type size_type;
151 
152  private:
153  typedef typename _Alloc::template rebind<Mapped> __rebind_m;
154  typedef typename __rebind_m::other __rebind_ma;
156  typedef typename _Alloc::template rebind<__value_type> __rebind_v;
157  typedef typename __rebind_v::other __rebind_va;
158 
159  public:
160  typedef typename __rebind_ma::value_type mapped_type;
161  typedef typename __rebind_ma::pointer mapped_pointer;
162  typedef typename __rebind_ma::const_pointer mapped_const_pointer;
163  typedef typename __rebind_ma::reference mapped_reference;
164  typedef typename __rebind_ma::const_reference mapped_const_reference;
165 
166  typedef typename __rebind_va::value_type value_type;
167  typedef typename __rebind_va::pointer pointer;
168  typedef typename __rebind_va::const_pointer const_pointer;
169  typedef typename __rebind_va::reference reference;
170  typedef typename __rebind_va::const_reference const_reference;
171 
173  };
174 
175 
176  /**
177  * Specialization of type_base for the case where the hash value
178  * is not stored alongside each value.
179  */
180  template<typename Key, typename _Alloc>
181  struct type_base<Key, null_type, _Alloc, false>
182  {
183  public:
184  typedef typename _Alloc::size_type size_type;
185  typedef Key value_type;
186 
187  private:
188  typedef typename _Alloc::template rebind<null_type> __rebind_m;
189  typedef typename __rebind_m::other __rebind_ma;
190  typedef typename _Alloc::template rebind<value_type> __rebind_v;
191  typedef typename __rebind_v::other __rebind_va;
192 
193  public:
194  typedef typename __rebind_ma::value_type mapped_type;
195  typedef typename __rebind_ma::pointer mapped_pointer;
196  typedef typename __rebind_ma::const_pointer mapped_const_pointer;
197  typedef typename __rebind_ma::reference mapped_reference;
198  typedef typename __rebind_ma::const_reference mapped_const_reference;
199 
200  typedef typename __rebind_va::pointer pointer;
201  typedef typename __rebind_va::const_pointer const_pointer;
202  typedef typename __rebind_va::reference reference;
203  typedef typename __rebind_va::const_reference const_reference;
204 
206 
207  static null_type s_null_type;
208  };
209 
210  template<typename Key, typename _Alloc>
211  null_type
212  type_base<Key, null_type, _Alloc, false>::s_null_type;
213 
214 
215  /**
216  * Specialization of type_base for the case where the hash value
217  * is stored alongside each value.
218  */
219  template<typename Key, typename _Alloc>
220  struct type_base<Key, null_type, _Alloc, true>
221  {
222  public:
223  typedef typename _Alloc::size_type size_type;
224  typedef Key value_type;
225 
226  private:
227  typedef typename _Alloc::template rebind<null_type> __rebind_m;
228  typedef typename __rebind_m::other __rebind_ma;
229  typedef typename _Alloc::template rebind<value_type> __rebind_v;
230  typedef typename __rebind_v::other __rebind_va;
231 
232  public:
233  typedef typename __rebind_ma::value_type mapped_type;
234  typedef typename __rebind_ma::pointer mapped_pointer;
235  typedef typename __rebind_ma::const_pointer mapped_const_pointer;
236  typedef typename __rebind_ma::reference mapped_reference;
237  typedef typename __rebind_ma::const_reference mapped_const_reference;
238 
239  typedef typename __rebind_va::pointer pointer;
240  typedef typename __rebind_va::const_pointer const_pointer;
241  typedef typename __rebind_va::reference reference;
242  typedef typename __rebind_va::const_reference const_reference;
243 
245 
246  static null_type s_null_type;
247  };
248 
249  template<typename Key, typename _Alloc>
250  null_type
251  type_base<Key, null_type, _Alloc, true>::s_null_type;
252 
253 
254  /// Type base dispatch.
255  template<typename Key, typename Mapped, typename _Alloc, bool Store_Hash>
257  {
258  typedef type_base<Key, Mapped, _Alloc, Store_Hash> type;
259  };
260 
261  /// Traits for abstract types.
262  template<typename Key, typename Mapped, typename _Alloc, bool Store_Hash>
264  : public type_dispatch<Key, Mapped, _Alloc, Store_Hash>::type
265  {
266  private:
268  typedef typename _Alloc::template rebind<Key>::other __rebind_a;
269 
270  public:
271  typedef typename _Alloc::size_type size_type;
272  typedef typename __rebind_a::value_type key_type;
273  typedef typename __rebind_a::pointer key_pointer;
274  typedef typename __rebind_a::const_pointer key_const_pointer;
275  typedef typename __rebind_a::reference key_reference;
276  typedef typename __rebind_a::const_reference key_const_reference;
278  typedef integral_constant<int, Store_Hash> store_extra;
279  typedef typename __nothrowcopy::indicator no_throw_indicator;
280 
281  store_extra m_store_extra_indicator;
282  no_throw_indicator m_no_throw_copies_indicator;
283  };
284  //@}
285  } // namespace detail
286 } // namespace __gnu_pbds
287 
288 #endif