libstdc++
boost_concept_check.h
Go to the documentation of this file.
1 // -*- C++ -*-
2 
3 // Copyright (C) 2004, 2005, 2006, 2007, 2009 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
7 // terms of the GNU General Public License as published by the
8 // Free Software Foundation; either version 3, or (at your option)
9 // any later version.
10 
11 // This library is distributed in the hope that it will be useful,
12 // but WITHOUT ANY WARRANTY; without even the implied warranty of
13 // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
14 // GNU 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 // (C) Copyright Jeremy Siek 2000. Permission to copy, use, modify,
26 // sell and distribute this software is granted provided this
27 // copyright notice appears in all copies. This software is provided
28 // "as is" without express or implied warranty, and with no claim as
29 // to its suitability for any purpose.
30 //
31 
32 /** @file boost_concept_check.h
33  * This is an internal header file, included by other library headers.
34  * You should not attempt to use it directly.
35  */
36 
37 // GCC Note: based on version 1.12.0 of the Boost library.
38 
39 #ifndef _BOOST_CONCEPT_CHECK_H
40 #define _BOOST_CONCEPT_CHECK_H 1
41 
42 #pragma GCC system_header
43 
44 #include <cstddef> // for ptrdiff_t, used next
45 #include <bits/stl_iterator_base_types.h> // for traits and tags
46 
47 _GLIBCXX_BEGIN_NAMESPACE(__gnu_cxx)
48 
49 #define _IsUnused __attribute__ ((__unused__))
50 
51 // When the C-C code is in use, we would like this function to do as little
52 // as possible at runtime, use as few resources as possible, and hopefully
53 // be elided out of existence... hmmm.
54 template <class _Concept>
55 inline void __function_requires()
56 {
57  void (_Concept::*__x)() _IsUnused = &_Concept::__constraints;
58 }
59 
60 // No definition: if this is referenced, there's a problem with
61 // the instantiating type not being one of the required integer types.
62 // Unfortunately, this results in a link-time error, not a compile-time error.
63 void __error_type_must_be_an_integer_type();
64 void __error_type_must_be_an_unsigned_integer_type();
65 void __error_type_must_be_a_signed_integer_type();
66 
67 // ??? Should the "concept_checking*" structs begin with more than _ ?
68 #define _GLIBCXX_CLASS_REQUIRES(_type_var, _ns, _concept) \
69  typedef void (_ns::_concept <_type_var>::* _func##_type_var##_concept)(); \
70  template <_func##_type_var##_concept _Tp1> \
71  struct _concept_checking##_type_var##_concept { }; \
72  typedef _concept_checking##_type_var##_concept< \
73  &_ns::_concept <_type_var>::__constraints> \
74  _concept_checking_typedef##_type_var##_concept
75 
76 #define _GLIBCXX_CLASS_REQUIRES2(_type_var1, _type_var2, _ns, _concept) \
77  typedef void (_ns::_concept <_type_var1,_type_var2>::* _func##_type_var1##_type_var2##_concept)(); \
78  template <_func##_type_var1##_type_var2##_concept _Tp1> \
79  struct _concept_checking##_type_var1##_type_var2##_concept { }; \
80  typedef _concept_checking##_type_var1##_type_var2##_concept< \
81  &_ns::_concept <_type_var1,_type_var2>::__constraints> \
82  _concept_checking_typedef##_type_var1##_type_var2##_concept
83 
84 #define _GLIBCXX_CLASS_REQUIRES3(_type_var1, _type_var2, _type_var3, _ns, _concept) \
85  typedef void (_ns::_concept <_type_var1,_type_var2,_type_var3>::* _func##_type_var1##_type_var2##_type_var3##_concept)(); \
86  template <_func##_type_var1##_type_var2##_type_var3##_concept _Tp1> \
87  struct _concept_checking##_type_var1##_type_var2##_type_var3##_concept { }; \
88  typedef _concept_checking##_type_var1##_type_var2##_type_var3##_concept< \
89  &_ns::_concept <_type_var1,_type_var2,_type_var3>::__constraints> \
90  _concept_checking_typedef##_type_var1##_type_var2##_type_var3##_concept
91 
92 #define _GLIBCXX_CLASS_REQUIRES4(_type_var1, _type_var2, _type_var3, _type_var4, _ns, _concept) \
93  typedef void (_ns::_concept <_type_var1,_type_var2,_type_var3,_type_var4>::* _func##_type_var1##_type_var2##_type_var3##_type_var4##_concept)(); \
94  template <_func##_type_var1##_type_var2##_type_var3##_type_var4##_concept _Tp1> \
95  struct _concept_checking##_type_var1##_type_var2##_type_var3##_type_var4##_concept { }; \
96  typedef _concept_checking##_type_var1##_type_var2##_type_var3##_type_var4##_concept< \
97  &_ns::_concept <_type_var1,_type_var2,_type_var3,_type_var4>::__constraints> \
98  _concept_checking_typedef##_type_var1##_type_var2##_type_var3##_type_var4##_concept
99 
100 
101 template <class _Tp1, class _Tp2>
102 struct _Aux_require_same { };
103 
104 template <class _Tp>
105 struct _Aux_require_same<_Tp,_Tp> { typedef _Tp _Type; };
106 
107  template <class _Tp1, class _Tp2>
108  struct _SameTypeConcept
109  {
110  void __constraints() {
111  typedef typename _Aux_require_same<_Tp1, _Tp2>::_Type _Required;
112  }
113  };
114 
115  template <class _Tp>
116  struct _IntegerConcept {
117  void __constraints() {
118  __error_type_must_be_an_integer_type();
119  }
120  };
121  template <> struct _IntegerConcept<short> { void __constraints() {} };
122  template <> struct _IntegerConcept<unsigned short> { void __constraints(){} };
123  template <> struct _IntegerConcept<int> { void __constraints() {} };
124  template <> struct _IntegerConcept<unsigned int> { void __constraints() {} };
125  template <> struct _IntegerConcept<long> { void __constraints() {} };
126  template <> struct _IntegerConcept<unsigned long> { void __constraints() {} };
127  template <> struct _IntegerConcept<long long> { void __constraints() {} };
128  template <> struct _IntegerConcept<unsigned long long>
129  { void __constraints() {} };
130 
131  template <class _Tp>
132  struct _SignedIntegerConcept {
133  void __constraints() {
134  __error_type_must_be_a_signed_integer_type();
135  }
136  };
137  template <> struct _SignedIntegerConcept<short> { void __constraints() {} };
138  template <> struct _SignedIntegerConcept<int> { void __constraints() {} };
139  template <> struct _SignedIntegerConcept<long> { void __constraints() {} };
140  template <> struct _SignedIntegerConcept<long long> { void __constraints(){}};
141 
142  template <class _Tp>
143  struct _UnsignedIntegerConcept {
144  void __constraints() {
145  __error_type_must_be_an_unsigned_integer_type();
146  }
147  };
148  template <> struct _UnsignedIntegerConcept<unsigned short>
149  { void __constraints() {} };
150  template <> struct _UnsignedIntegerConcept<unsigned int>
151  { void __constraints() {} };
152  template <> struct _UnsignedIntegerConcept<unsigned long>
153  { void __constraints() {} };
154  template <> struct _UnsignedIntegerConcept<unsigned long long>
155  { void __constraints() {} };
156 
157  //===========================================================================
158  // Basic Concepts
159 
160  template <class _Tp>
161  struct _DefaultConstructibleConcept
162  {
163  void __constraints() {
164  _Tp __a _IsUnused; // require default constructor
165  }
166  };
167 
168  template <class _Tp>
169  struct _AssignableConcept
170  {
171  void __constraints() {
172  __a = __a; // require assignment operator
173  __const_constraints(__a);
174  }
175  void __const_constraints(const _Tp& __b) {
176  __a = __b; // const required for argument to assignment
177  }
178  _Tp __a;
179  // possibly should be "Tp* a;" and then dereference "a" in constraint
180  // functions? present way would require a default ctor, i think...
181  };
182 
183  template <class _Tp>
184  struct _CopyConstructibleConcept
185  {
186  void __constraints() {
187  _Tp __a(__b); // require copy constructor
188  _Tp* __ptr _IsUnused = &__a; // require address of operator
189  __const_constraints(__a);
190  }
191  void __const_constraints(const _Tp& __a) {
192  _Tp __c _IsUnused(__a); // require const copy constructor
193  const _Tp* __ptr _IsUnused = &__a; // require const address of operator
194  }
195  _Tp __b;
196  };
197 
198  // The SGI STL version of Assignable requires copy constructor and operator=
199  template <class _Tp>
200  struct _SGIAssignableConcept
201  {
202  void __constraints() {
203  _Tp __b _IsUnused(__a);
204  __a = __a; // require assignment operator
205  __const_constraints(__a);
206  }
207  void __const_constraints(const _Tp& __b) {
208  _Tp __c _IsUnused(__b);
209  __a = __b; // const required for argument to assignment
210  }
211  _Tp __a;
212  };
213 
214  template <class _From, class _To>
215  struct _ConvertibleConcept
216  {
217  void __constraints() {
218  _To __y _IsUnused = __x;
219  }
220  _From __x;
221  };
222 
223  // The C++ standard requirements for many concepts talk about return
224  // types that must be "convertible to bool". The problem with this
225  // requirement is that it leaves the door open for evil proxies that
226  // define things like operator|| with strange return types. Two
227  // possible solutions are:
228  // 1) require the return type to be exactly bool
229  // 2) stay with convertible to bool, and also
230  // specify stuff about all the logical operators.
231  // For now we just test for convertible to bool.
232  template <class _Tp>
233  void __aux_require_boolean_expr(const _Tp& __t) {
234  bool __x _IsUnused = __t;
235  }
236 
237 // FIXME
238  template <class _Tp>
239  struct _EqualityComparableConcept
240  {
241  void __constraints() {
242  __aux_require_boolean_expr(__a == __b);
243  }
244  _Tp __a, __b;
245  };
246 
247  template <class _Tp>
248  struct _LessThanComparableConcept
249  {
250  void __constraints() {
251  __aux_require_boolean_expr(__a < __b);
252  }
253  _Tp __a, __b;
254  };
255 
256  // This is equivalent to SGI STL's LessThanComparable.
257  template <class _Tp>
258  struct _ComparableConcept
259  {
260  void __constraints() {
261  __aux_require_boolean_expr(__a < __b);
262  __aux_require_boolean_expr(__a > __b);
263  __aux_require_boolean_expr(__a <= __b);
264  __aux_require_boolean_expr(__a >= __b);
265  }
266  _Tp __a, __b;
267  };
268 
269 #define _GLIBCXX_DEFINE_BINARY_PREDICATE_OP_CONSTRAINT(_OP,_NAME) \
270  template <class _First, class _Second> \
271  struct _NAME { \
272  void __constraints() { (void)__constraints_(); } \
273  bool __constraints_() { \
274  return __a _OP __b; \
275  } \
276  _First __a; \
277  _Second __b; \
278  }
279 
280 #define _GLIBCXX_DEFINE_BINARY_OPERATOR_CONSTRAINT(_OP,_NAME) \
281  template <class _Ret, class _First, class _Second> \
282  struct _NAME { \
283  void __constraints() { (void)__constraints_(); } \
284  _Ret __constraints_() { \
285  return __a _OP __b; \
286  } \
287  _First __a; \
288  _Second __b; \
289  }
290 
291  _GLIBCXX_DEFINE_BINARY_PREDICATE_OP_CONSTRAINT(==, _EqualOpConcept);
292  _GLIBCXX_DEFINE_BINARY_PREDICATE_OP_CONSTRAINT(!=, _NotEqualOpConcept);
293  _GLIBCXX_DEFINE_BINARY_PREDICATE_OP_CONSTRAINT(<, _LessThanOpConcept);
294  _GLIBCXX_DEFINE_BINARY_PREDICATE_OP_CONSTRAINT(<=, _LessEqualOpConcept);
295  _GLIBCXX_DEFINE_BINARY_PREDICATE_OP_CONSTRAINT(>, _GreaterThanOpConcept);
296  _GLIBCXX_DEFINE_BINARY_PREDICATE_OP_CONSTRAINT(>=, _GreaterEqualOpConcept);
297 
298  _GLIBCXX_DEFINE_BINARY_OPERATOR_CONSTRAINT(+, _PlusOpConcept);
299  _GLIBCXX_DEFINE_BINARY_OPERATOR_CONSTRAINT(*, _TimesOpConcept);
300  _GLIBCXX_DEFINE_BINARY_OPERATOR_CONSTRAINT(/, _DivideOpConcept);
301  _GLIBCXX_DEFINE_BINARY_OPERATOR_CONSTRAINT(-, _SubtractOpConcept);
302  _GLIBCXX_DEFINE_BINARY_OPERATOR_CONSTRAINT(%, _ModOpConcept);
303 
304 #undef _GLIBCXX_DEFINE_BINARY_PREDICATE_OP_CONSTRAINT
305 #undef _GLIBCXX_DEFINE_BINARY_OPERATOR_CONSTRAINT
306 
307  //===========================================================================
308  // Function Object Concepts
309 
310  template <class _Func, class _Return>
311  struct _GeneratorConcept
312  {
313  void __constraints() {
314  const _Return& __r _IsUnused = __f();// require operator() member function
315  }
316  _Func __f;
317  };
318 
319 
320  template <class _Func>
321  struct _GeneratorConcept<_Func,void>
322  {
323  void __constraints() {
324  __f(); // require operator() member function
325  }
326  _Func __f;
327  };
328 
329  template <class _Func, class _Return, class _Arg>
330  struct _UnaryFunctionConcept
331  {
332  void __constraints() {
333  __r = __f(__arg); // require operator()
334  }
335  _Func __f;
336  _Arg __arg;
337  _Return __r;
338  };
339 
340  template <class _Func, class _Arg>
341  struct _UnaryFunctionConcept<_Func, void, _Arg> {
342  void __constraints() {
343  __f(__arg); // require operator()
344  }
345  _Func __f;
346  _Arg __arg;
347  };
348 
349  template <class _Func, class _Return, class _First, class _Second>
350  struct _BinaryFunctionConcept
351  {
352  void __constraints() {
353  __r = __f(__first, __second); // require operator()
354  }
355  _Func __f;
356  _First __first;
357  _Second __second;
358  _Return __r;
359  };
360 
361  template <class _Func, class _First, class _Second>
362  struct _BinaryFunctionConcept<_Func, void, _First, _Second>
363  {
364  void __constraints() {
365  __f(__first, __second); // require operator()
366  }
367  _Func __f;
368  _First __first;
369  _Second __second;
370  };
371 
372  template <class _Func, class _Arg>
373  struct _UnaryPredicateConcept
374  {
375  void __constraints() {
376  __aux_require_boolean_expr(__f(__arg)); // require op() returning bool
377  }
378  _Func __f;
379  _Arg __arg;
380  };
381 
382  template <class _Func, class _First, class _Second>
383  struct _BinaryPredicateConcept
384  {
385  void __constraints() {
386  __aux_require_boolean_expr(__f(__a, __b)); // require op() returning bool
387  }
388  _Func __f;
389  _First __a;
390  _Second __b;
391  };
392 
393  // use this when functor is used inside a container class like std::set
394  template <class _Func, class _First, class _Second>
395  struct _Const_BinaryPredicateConcept {
396  void __constraints() {
397  __const_constraints(__f);
398  }
399  void __const_constraints(const _Func& __fun) {
400  __function_requires<_BinaryPredicateConcept<_Func, _First, _Second> >();
401  // operator() must be a const member function
402  __aux_require_boolean_expr(__fun(__a, __b));
403  }
404  _Func __f;
405  _First __a;
406  _Second __b;
407  };
408 
409  //===========================================================================
410  // Iterator Concepts
411 
412  template <class _Tp>
413  struct _TrivialIteratorConcept
414  {
415  void __constraints() {
416 // __function_requires< _DefaultConstructibleConcept<_Tp> >();
417  __function_requires< _AssignableConcept<_Tp> >();
418  __function_requires< _EqualityComparableConcept<_Tp> >();
419 // typedef typename std::iterator_traits<_Tp>::value_type _V;
420  (void)*__i; // require dereference operator
421  }
422  _Tp __i;
423  };
424 
425  template <class _Tp>
426  struct _Mutable_TrivialIteratorConcept
427  {
428  void __constraints() {
429  __function_requires< _TrivialIteratorConcept<_Tp> >();
430  *__i = *__j; // require dereference and assignment
431  }
432  _Tp __i, __j;
433  };
434 
435  template <class _Tp>
436  struct _InputIteratorConcept
437  {
438  void __constraints() {
439  __function_requires< _TrivialIteratorConcept<_Tp> >();
440  // require iterator_traits typedef's
441  typedef typename std::iterator_traits<_Tp>::difference_type _Diff;
442 // __function_requires< _SignedIntegerConcept<_Diff> >();
443  typedef typename std::iterator_traits<_Tp>::reference _Ref;
444  typedef typename std::iterator_traits<_Tp>::pointer _Pt;
445  typedef typename std::iterator_traits<_Tp>::iterator_category _Cat;
446  __function_requires< _ConvertibleConcept<
447  typename std::iterator_traits<_Tp>::iterator_category,
449  ++__i; // require preincrement operator
450  __i++; // require postincrement operator
451  }
452  _Tp __i;
453  };
454 
455  template <class _Tp, class _ValueT>
456  struct _OutputIteratorConcept
457  {
458  void __constraints() {
459  __function_requires< _AssignableConcept<_Tp> >();
460  ++__i; // require preincrement operator
461  __i++; // require postincrement operator
462  *__i++ = __t; // require postincrement and assignment
463  }
464  _Tp __i;
465  _ValueT __t;
466  };
467 
468  template <class _Tp>
469  struct _ForwardIteratorConcept
470  {
471  void __constraints() {
472  __function_requires< _InputIteratorConcept<_Tp> >();
473  __function_requires< _DefaultConstructibleConcept<_Tp> >();
474  __function_requires< _ConvertibleConcept<
475  typename std::iterator_traits<_Tp>::iterator_category,
477  typedef typename std::iterator_traits<_Tp>::reference _Ref;
478  _Ref __r _IsUnused = *__i;
479  }
480  _Tp __i;
481  };
482 
483  template <class _Tp>
484  struct _Mutable_ForwardIteratorConcept
485  {
486  void __constraints() {
487  __function_requires< _ForwardIteratorConcept<_Tp> >();
488  *__i++ = *__i; // require postincrement and assignment
489  }
490  _Tp __i;
491  };
492 
493  template <class _Tp>
494  struct _BidirectionalIteratorConcept
495  {
496  void __constraints() {
497  __function_requires< _ForwardIteratorConcept<_Tp> >();
498  __function_requires< _ConvertibleConcept<
499  typename std::iterator_traits<_Tp>::iterator_category,
501  --__i; // require predecrement operator
502  __i--; // require postdecrement operator
503  }
504  _Tp __i;
505  };
506 
507  template <class _Tp>
508  struct _Mutable_BidirectionalIteratorConcept
509  {
510  void __constraints() {
511  __function_requires< _BidirectionalIteratorConcept<_Tp> >();
512  __function_requires< _Mutable_ForwardIteratorConcept<_Tp> >();
513  *__i-- = *__i; // require postdecrement and assignment
514  }
515  _Tp __i;
516  };
517 
518 
519  template <class _Tp>
520  struct _RandomAccessIteratorConcept
521  {
522  void __constraints() {
523  __function_requires< _BidirectionalIteratorConcept<_Tp> >();
524  __function_requires< _ComparableConcept<_Tp> >();
525  __function_requires< _ConvertibleConcept<
526  typename std::iterator_traits<_Tp>::iterator_category,
528  // ??? We don't use _Ref, are we just checking for "referenceability"?
529  typedef typename std::iterator_traits<_Tp>::reference _Ref;
530 
531  __i += __n; // require assignment addition operator
532  __i = __i + __n; __i = __n + __i; // require addition with difference type
533  __i -= __n; // require assignment subtraction op
534  __i = __i - __n; // require subtraction with
535  // difference type
536  __n = __i - __j; // require difference operator
537  (void)__i[__n]; // require element access operator
538  }
539  _Tp __a, __b;
540  _Tp __i, __j;
541  typename std::iterator_traits<_Tp>::difference_type __n;
542  };
543 
544  template <class _Tp>
545  struct _Mutable_RandomAccessIteratorConcept
546  {
547  void __constraints() {
548  __function_requires< _RandomAccessIteratorConcept<_Tp> >();
549  __function_requires< _Mutable_BidirectionalIteratorConcept<_Tp> >();
550  __i[__n] = *__i; // require element access and assignment
551  }
552  _Tp __i;
553  typename std::iterator_traits<_Tp>::difference_type __n;
554  };
555 
556  //===========================================================================
557  // Container Concepts
558 
559  template <class _Container>
560  struct _ContainerConcept
561  {
562  typedef typename _Container::value_type _Value_type;
563  typedef typename _Container::difference_type _Difference_type;
564  typedef typename _Container::size_type _Size_type;
565  typedef typename _Container::const_reference _Const_reference;
566  typedef typename _Container::const_pointer _Const_pointer;
567  typedef typename _Container::const_iterator _Const_iterator;
568 
569  void __constraints() {
570  __function_requires< _InputIteratorConcept<_Const_iterator> >();
571  __function_requires< _AssignableConcept<_Container> >();
572  const _Container __c;
573  __i = __c.begin();
574  __i = __c.end();
575  __n = __c.size();
576  __n = __c.max_size();
577  __b = __c.empty();
578  }
579  bool __b;
580  _Const_iterator __i;
581  _Size_type __n;
582  };
583 
584  template <class _Container>
585  struct _Mutable_ContainerConcept
586  {
587  typedef typename _Container::value_type _Value_type;
588  typedef typename _Container::reference _Reference;
589  typedef typename _Container::iterator _Iterator;
590  typedef typename _Container::pointer _Pointer;
591 
592  void __constraints() {
593  __function_requires< _ContainerConcept<_Container> >();
594  __function_requires< _AssignableConcept<_Value_type> >();
595  __function_requires< _InputIteratorConcept<_Iterator> >();
596 
597  __i = __c.begin();
598  __i = __c.end();
599  __c.swap(__c2);
600  }
601  _Iterator __i;
602  _Container __c, __c2;
603  };
604 
605  template <class _ForwardContainer>
606  struct _ForwardContainerConcept
607  {
608  void __constraints() {
609  __function_requires< _ContainerConcept<_ForwardContainer> >();
610  typedef typename _ForwardContainer::const_iterator _Const_iterator;
611  __function_requires< _ForwardIteratorConcept<_Const_iterator> >();
612  }
613  };
614 
615  template <class _ForwardContainer>
616  struct _Mutable_ForwardContainerConcept
617  {
618  void __constraints() {
619  __function_requires< _ForwardContainerConcept<_ForwardContainer> >();
620  __function_requires< _Mutable_ContainerConcept<_ForwardContainer> >();
621  typedef typename _ForwardContainer::iterator _Iterator;
622  __function_requires< _Mutable_ForwardIteratorConcept<_Iterator> >();
623  }
624  };
625 
626  template <class _ReversibleContainer>
627  struct _ReversibleContainerConcept
628  {
629  typedef typename _ReversibleContainer::const_iterator _Const_iterator;
630  typedef typename _ReversibleContainer::const_reverse_iterator
631  _Const_reverse_iterator;
632 
633  void __constraints() {
634  __function_requires< _ForwardContainerConcept<_ReversibleContainer> >();
635  __function_requires< _BidirectionalIteratorConcept<_Const_iterator> >();
636  __function_requires<
637  _BidirectionalIteratorConcept<_Const_reverse_iterator> >();
638 
639  const _ReversibleContainer __c;
640  _Const_reverse_iterator __i = __c.rbegin();
641  __i = __c.rend();
642  }
643  };
644 
645  template <class _ReversibleContainer>
646  struct _Mutable_ReversibleContainerConcept
647  {
648  typedef typename _ReversibleContainer::iterator _Iterator;
649  typedef typename _ReversibleContainer::reverse_iterator _Reverse_iterator;
650 
651  void __constraints() {
652  __function_requires<_ReversibleContainerConcept<_ReversibleContainer> >();
653  __function_requires<
654  _Mutable_ForwardContainerConcept<_ReversibleContainer> >();
655  __function_requires<_Mutable_BidirectionalIteratorConcept<_Iterator> >();
656  __function_requires<
657  _Mutable_BidirectionalIteratorConcept<_Reverse_iterator> >();
658 
659  _Reverse_iterator __i = __c.rbegin();
660  __i = __c.rend();
661  }
662  _ReversibleContainer __c;
663  };
664 
665  template <class _RandomAccessContainer>
666  struct _RandomAccessContainerConcept
667  {
668  typedef typename _RandomAccessContainer::size_type _Size_type;
669  typedef typename _RandomAccessContainer::const_reference _Const_reference;
670  typedef typename _RandomAccessContainer::const_iterator _Const_iterator;
671  typedef typename _RandomAccessContainer::const_reverse_iterator
672  _Const_reverse_iterator;
673 
674  void __constraints() {
675  __function_requires<
676  _ReversibleContainerConcept<_RandomAccessContainer> >();
677  __function_requires< _RandomAccessIteratorConcept<_Const_iterator> >();
678  __function_requires<
679  _RandomAccessIteratorConcept<_Const_reverse_iterator> >();
680 
681  const _RandomAccessContainer __c;
682  _Const_reference __r _IsUnused = __c[__n];
683  }
684  _Size_type __n;
685  };
686 
687  template <class _RandomAccessContainer>
688  struct _Mutable_RandomAccessContainerConcept
689  {
690  typedef typename _RandomAccessContainer::size_type _Size_type;
691  typedef typename _RandomAccessContainer::reference _Reference;
692  typedef typename _RandomAccessContainer::iterator _Iterator;
693  typedef typename _RandomAccessContainer::reverse_iterator _Reverse_iterator;
694 
695  void __constraints() {
696  __function_requires<
697  _RandomAccessContainerConcept<_RandomAccessContainer> >();
698  __function_requires<
699  _Mutable_ReversibleContainerConcept<_RandomAccessContainer> >();
700  __function_requires< _Mutable_RandomAccessIteratorConcept<_Iterator> >();
701  __function_requires<
702  _Mutable_RandomAccessIteratorConcept<_Reverse_iterator> >();
703 
704  _Reference __r _IsUnused = __c[__i];
705  }
706  _Size_type __i;
707  _RandomAccessContainer __c;
708  };
709 
710  // A Sequence is inherently mutable
711  template <class _Sequence>
712  struct _SequenceConcept
713  {
714  typedef typename _Sequence::reference _Reference;
715  typedef typename _Sequence::const_reference _Const_reference;
716 
717  void __constraints() {
718  // Matt Austern's book puts DefaultConstructible here, the C++
719  // standard places it in Container
720  // function_requires< DefaultConstructible<Sequence> >();
721  __function_requires< _Mutable_ForwardContainerConcept<_Sequence> >();
722  __function_requires< _DefaultConstructibleConcept<_Sequence> >();
723 
724  _Sequence
725  __c _IsUnused(__n, __t),
726  __c2 _IsUnused(__first, __last);
727 
728  __c.insert(__p, __t);
729  __c.insert(__p, __n, __t);
730  __c.insert(__p, __first, __last);
731 
732  __c.erase(__p);
733  __c.erase(__p, __q);
734 
735  _Reference __r _IsUnused = __c.front();
736 
737  __const_constraints(__c);
738  }
739  void __const_constraints(const _Sequence& __c) {
740  _Const_reference __r _IsUnused = __c.front();
741  }
742  typename _Sequence::value_type __t;
743  typename _Sequence::size_type __n;
744  typename _Sequence::value_type *__first, *__last;
745  typename _Sequence::iterator __p, __q;
746  };
747 
748  template <class _FrontInsertionSequence>
749  struct _FrontInsertionSequenceConcept
750  {
751  void __constraints() {
752  __function_requires< _SequenceConcept<_FrontInsertionSequence> >();
753 
754  __c.push_front(__t);
755  __c.pop_front();
756  }
757  _FrontInsertionSequence __c;
758  typename _FrontInsertionSequence::value_type __t;
759  };
760 
761  template <class _BackInsertionSequence>
762  struct _BackInsertionSequenceConcept
763  {
764  typedef typename _BackInsertionSequence::reference _Reference;
765  typedef typename _BackInsertionSequence::const_reference _Const_reference;
766 
767  void __constraints() {
768  __function_requires< _SequenceConcept<_BackInsertionSequence> >();
769 
770  __c.push_back(__t);
771  __c.pop_back();
772  _Reference __r _IsUnused = __c.back();
773  }
774  void __const_constraints(const _BackInsertionSequence& __c) {
775  _Const_reference __r _IsUnused = __c.back();
776  };
777  _BackInsertionSequence __c;
778  typename _BackInsertionSequence::value_type __t;
779  };
780 
781 _GLIBCXX_END_NAMESPACE
782 
783 #undef _IsUnused
784 
785 #endif // _GLIBCXX_BOOST_CONCEPT_CHECK
786 
787 
Bidirectional iterators support a superset of forward iterator operations.
Marking input iterators.
Random-access iterators support a superset of bidirectional iterator operations.
Forward iterators support a superset of input iterator operations.