OSDN Git Service

2011-03-14 Benjamin Kosnik <bkoz@redhat.com>
[pf3gnuchains/gcc-fork.git] / libstdc++-v3 / include / bits / cpp_type_traits.h
1 // The  -*- C++ -*- type traits classes for internal use in libstdc++
2
3 // Copyright (C) 2000, 2001, 2002, 2003, 2004, 2005, 2006, 2007, 2009, 2010
4 // Free Software Foundation, Inc.
5 //
6 // This file is part of the GNU ISO C++ Library.  This library is free
7 // software; you can redistribute it and/or modify it under the
8 // terms of the GNU General Public License as published by the
9 // Free Software Foundation; either version 3, or (at your option)
10 // any later version.
11
12 // This library is distributed in the hope that it will be useful,
13 // but WITHOUT ANY WARRANTY; without even the implied warranty of
14 // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
15 // GNU General Public License for more details.
16
17 // Under Section 7 of GPL version 3, you are granted additional
18 // permissions described in the GCC Runtime Library Exception, version
19 // 3.1, as published by the Free Software Foundation.
20
21 // You should have received a copy of the GNU General Public License and
22 // a copy of the GCC Runtime Library Exception along with this program;
23 // see the files COPYING3 and COPYING.RUNTIME respectively.  If not, see
24 // <http://www.gnu.org/licenses/>.
25
26 /** @file bits/cpp_type_traits.h
27  *  This is an internal header file, included by other library headers.
28  *  Do not attempt to use it directly. @headername{ext/type_traits}
29  */
30
31 // Written by Gabriel Dos Reis <dosreis@cmla.ens-cachan.fr>
32
33 #ifndef _CPP_TYPE_TRAITS_H
34 #define _CPP_TYPE_TRAITS_H 1
35
36 #pragma GCC system_header
37
38 #include <bits/c++config.h>
39
40 //
41 // This file provides some compile-time information about various types.
42 // These representations were designed, on purpose, to be constant-expressions
43 // and not types as found in <bits/type_traits.h>.  In particular, they
44 // can be used in control structures and the optimizer hopefully will do
45 // the obvious thing.
46 //
47 // Why integral expressions, and not functions nor types?
48 // Firstly, these compile-time entities are used as template-arguments
49 // so function return values won't work:  We need compile-time entities.
50 // We're left with types and constant  integral expressions.
51 // Secondly, from the point of view of ease of use, type-based compile-time
52 // information is -not- *that* convenient.  On has to write lots of
53 // overloaded functions and to hope that the compiler will select the right
54 // one. As a net effect, the overall structure isn't very clear at first
55 // glance.
56 // Thirdly, partial ordering and overload resolution (of function templates)
57 // is highly costly in terms of compiler-resource.  It is a Good Thing to
58 // keep these resource consumption as least as possible.
59 //
60 // See valarray_array.h for a case use.
61 //
62 // -- Gaby (dosreis@cmla.ens-cachan.fr) 2000-03-06.
63 //
64 // Update 2005: types are also provided and <bits/type_traits.h> has been
65 // removed.
66 //
67
68 // Forward declaration hack, should really include this from somewhere.
69 namespace __gnu_cxx _GLIBCXX_VISIBILITY(default)
70 {
71 _GLIBCXX_BEGIN_NAMESPACE_VERSION
72
73   template<typename _Iterator, typename _Container>
74     class __normal_iterator;
75
76 _GLIBCXX_END_NAMESPACE_VERSION
77 } // namespace
78
79 namespace std _GLIBCXX_VISIBILITY(default)
80 {
81 _GLIBCXX_BEGIN_NAMESPACE_VERSION
82
83   struct __true_type { };
84   struct __false_type { };
85
86   template<bool>
87     struct __truth_type
88     { typedef __false_type __type; };
89
90   template<>
91     struct __truth_type<true>
92     { typedef __true_type __type; };
93
94   // N.B. The conversions to bool are needed due to the issue
95   // explained in c++/19404.
96   template<class _Sp, class _Tp>
97     struct __traitor
98     {
99       enum { __value = bool(_Sp::__value) || bool(_Tp::__value) };
100       typedef typename __truth_type<__value>::__type __type;
101     };
102
103   // Compare for equality of types.
104   template<typename, typename>
105     struct __are_same
106     {
107       enum { __value = 0 };
108       typedef __false_type __type;
109     };
110
111   template<typename _Tp>
112     struct __are_same<_Tp, _Tp>
113     {
114       enum { __value = 1 };
115       typedef __true_type __type;
116     };
117
118   // Holds if the template-argument is a void type.
119   template<typename _Tp>
120     struct __is_void
121     {
122       enum { __value = 0 };
123       typedef __false_type __type;
124     };
125
126   template<>
127     struct __is_void<void>
128     {
129       enum { __value = 1 };
130       typedef __true_type __type;
131     };
132
133   //
134   // Integer types
135   //
136   template<typename _Tp>
137     struct __is_integer
138     {
139       enum { __value = 0 };
140       typedef __false_type __type;
141     };
142
143   // Thirteen specializations (yes there are eleven standard integer
144   // types; <em>long long</em> and <em>unsigned long long</em> are
145   // supported as extensions)
146   template<>
147     struct __is_integer<bool>
148     {
149       enum { __value = 1 };
150       typedef __true_type __type;
151     };
152
153   template<>
154     struct __is_integer<char>
155     {
156       enum { __value = 1 };
157       typedef __true_type __type;
158     };
159
160   template<>
161     struct __is_integer<signed char>
162     {
163       enum { __value = 1 };
164       typedef __true_type __type;
165     };
166
167   template<>
168     struct __is_integer<unsigned char>
169     {
170       enum { __value = 1 };
171       typedef __true_type __type;
172     };
173
174 # ifdef _GLIBCXX_USE_WCHAR_T
175   template<>
176     struct __is_integer<wchar_t>
177     {
178       enum { __value = 1 };
179       typedef __true_type __type;
180     };
181 # endif
182
183 #ifdef __GXX_EXPERIMENTAL_CXX0X__
184   template<>
185     struct __is_integer<char16_t>
186     {
187       enum { __value = 1 };
188       typedef __true_type __type;
189     };
190
191   template<>
192     struct __is_integer<char32_t>
193     {
194       enum { __value = 1 };
195       typedef __true_type __type;
196     };
197 #endif
198
199   template<>
200     struct __is_integer<short>
201     {
202       enum { __value = 1 };
203       typedef __true_type __type;
204     };
205
206   template<>
207     struct __is_integer<unsigned short>
208     {
209       enum { __value = 1 };
210       typedef __true_type __type;
211     };
212
213   template<>
214     struct __is_integer<int>
215     {
216       enum { __value = 1 };
217       typedef __true_type __type;
218     };
219
220   template<>
221     struct __is_integer<unsigned int>
222     {
223       enum { __value = 1 };
224       typedef __true_type __type;
225     };
226
227   template<>
228     struct __is_integer<long>
229     {
230       enum { __value = 1 };
231       typedef __true_type __type;
232     };
233
234   template<>
235     struct __is_integer<unsigned long>
236     {
237       enum { __value = 1 };
238       typedef __true_type __type;
239     };
240
241   template<>
242     struct __is_integer<long long>
243     {
244       enum { __value = 1 };
245       typedef __true_type __type;
246     };
247
248   template<>
249     struct __is_integer<unsigned long long>
250     {
251       enum { __value = 1 };
252       typedef __true_type __type;
253     };
254
255   //
256   // Floating point types
257   //
258   template<typename _Tp>
259     struct __is_floating
260     {
261       enum { __value = 0 };
262       typedef __false_type __type;
263     };
264
265   // three specializations (float, double and 'long double')
266   template<>
267     struct __is_floating<float>
268     {
269       enum { __value = 1 };
270       typedef __true_type __type;
271     };
272
273   template<>
274     struct __is_floating<double>
275     {
276       enum { __value = 1 };
277       typedef __true_type __type;
278     };
279
280   template<>
281     struct __is_floating<long double>
282     {
283       enum { __value = 1 };
284       typedef __true_type __type;
285     };
286
287   //
288   // Pointer types
289   //
290   template<typename _Tp>
291     struct __is_pointer
292     {
293       enum { __value = 0 };
294       typedef __false_type __type;
295     };
296
297   template<typename _Tp>
298     struct __is_pointer<_Tp*>
299     {
300       enum { __value = 1 };
301       typedef __true_type __type;
302     };
303
304   //
305   // Normal iterator type
306   //
307   template<typename _Tp>
308     struct __is_normal_iterator
309     {
310       enum { __value = 0 };
311       typedef __false_type __type;
312     };
313
314   template<typename _Iterator, typename _Container>
315     struct __is_normal_iterator< __gnu_cxx::__normal_iterator<_Iterator,
316                                                               _Container> >
317     {
318       enum { __value = 1 };
319       typedef __true_type __type;
320     };
321
322   //
323   // An arithmetic type is an integer type or a floating point type
324   //
325   template<typename _Tp>
326     struct __is_arithmetic
327     : public __traitor<__is_integer<_Tp>, __is_floating<_Tp> >
328     { };
329
330   //
331   // A fundamental type is `void' or and arithmetic type
332   //
333   template<typename _Tp>
334     struct __is_fundamental
335     : public __traitor<__is_void<_Tp>, __is_arithmetic<_Tp> >
336     { };
337
338   //
339   // A scalar type is an arithmetic type or a pointer type
340   // 
341   template<typename _Tp>
342     struct __is_scalar
343     : public __traitor<__is_arithmetic<_Tp>, __is_pointer<_Tp> >
344     { };
345
346   //
347   // For use in std::copy and std::find overloads for streambuf iterators.
348   //
349   template<typename _Tp>
350     struct __is_char
351     {
352       enum { __value = 0 };
353       typedef __false_type __type;
354     };
355
356   template<>
357     struct __is_char<char>
358     {
359       enum { __value = 1 };
360       typedef __true_type __type;
361     };
362
363 #ifdef _GLIBCXX_USE_WCHAR_T
364   template<>
365     struct __is_char<wchar_t>
366     {
367       enum { __value = 1 };
368       typedef __true_type __type;
369     };
370 #endif
371
372   template<typename _Tp>
373     struct __is_byte
374     {
375       enum { __value = 0 };
376       typedef __false_type __type;
377     };
378
379   template<>
380     struct __is_byte<char>
381     {
382       enum { __value = 1 };
383       typedef __true_type __type;
384     };
385
386   template<>
387     struct __is_byte<signed char>
388     {
389       enum { __value = 1 };
390       typedef __true_type __type;
391     };
392
393   template<>
394     struct __is_byte<unsigned char>
395     {
396       enum { __value = 1 };
397       typedef __true_type __type;
398     };
399
400   //
401   // Move iterator type
402   //
403   template<typename _Tp>
404     struct __is_move_iterator
405     {
406       enum { __value = 0 };
407       typedef __false_type __type;
408     };
409
410 #ifdef __GXX_EXPERIMENTAL_CXX0X__
411   template<typename _Iterator>
412     class move_iterator;
413
414   template<typename _Iterator>
415     struct __is_move_iterator< move_iterator<_Iterator> >
416     {
417       enum { __value = 1 };
418       typedef __true_type __type;
419     };
420 #endif
421
422 _GLIBCXX_END_NAMESPACE_VERSION
423 } // namespace
424
425 #endif //_CPP_TYPE_TRAITS_H