OpenCores
URL https://opencores.org/ocsvn/openrisc/openrisc/trunk

Subversion Repositories openrisc

[/] [openrisc/] [trunk/] [gnu-dev/] [or1k-gcc/] [libstdc++-v3/] [include/] [std/] [tuple] - Blame information for rev 742

Details | Compare with Previous | View Log

Line No. Rev Author Line
1 742 jeremybenn
//  -*- C++ -*-
2
 
3
// Copyright (C) 2007, 2008, 2009, 2010, 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
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
// .
24
 
25
/** @file include/tuple
26
 *  This is a Standard C++ Library header.
27
 */
28
 
29
#ifndef _GLIBCXX_TUPLE
30
#define _GLIBCXX_TUPLE 1
31
 
32
#pragma GCC system_header
33
 
34
#ifndef __GXX_EXPERIMENTAL_CXX0X__
35
# include 
36
#else
37
 
38
#include 
39
#include 
40
 
41
namespace std _GLIBCXX_VISIBILITY(default)
42
{
43
_GLIBCXX_BEGIN_NAMESPACE_VERSION
44
 
45
  // Adds a const reference to a non-reference type.
46
  template
47
    struct __add_c_ref
48
    { typedef const _Tp& type; };
49
 
50
  template
51
    struct __add_c_ref<_Tp&>
52
    { typedef _Tp& type; };
53
 
54
  // Adds a reference to a non-reference type.
55
  template
56
    struct __add_ref
57
    { typedef _Tp& type; };
58
 
59
  template
60
    struct __add_ref<_Tp&>
61
    { typedef _Tp& type; };
62
 
63
  // Adds an rvalue reference to a non-reference type.
64
  template
65
    struct __add_r_ref
66
    { typedef _Tp&& type; };
67
 
68
  template
69
    struct __add_r_ref<_Tp&>
70
    { typedef _Tp& type; };
71
 
72
  template
73
    struct _Head_base;
74
 
75
  template
76
    struct _Head_base<_Idx, _Head, true>
77
    : public _Head
78
    {
79
      constexpr _Head_base()
80
      : _Head() { }
81
 
82
      constexpr _Head_base(const _Head& __h)
83
      : _Head(__h) { }
84
 
85
      template
86
               enable_if
87
                                         __uses_alloc_base>::value>::type>
88
        constexpr _Head_base(_UHead&& __h)
89
        : _Head(std::forward<_UHead>(__h)) { }
90
 
91
      _Head_base(__uses_alloc0)
92
      : _Head() { }
93
 
94
      template
95
        _Head_base(__uses_alloc1<_Alloc> __a)
96
        : _Head(allocator_arg, *__a._M_a) { }
97
 
98
      template
99
        _Head_base(__uses_alloc2<_Alloc> __a)
100
        : _Head(*__a._M_a) { }
101
 
102
      template
103
        _Head_base(__uses_alloc0, _UHead&& __uhead)
104
        : _Head(std::forward<_UHead>(__uhead)) { }
105
 
106
      template
107
        _Head_base(__uses_alloc1<_Alloc> __a, _UHead&& __uhead)
108
        : _Head(allocator_arg, *__a._M_a, std::forward<_UHead>(__uhead)) { }
109
 
110
      template
111
        _Head_base(__uses_alloc2<_Alloc> __a, _UHead&& __uhead)
112
        : _Head(std::forward<_UHead>(__uhead), *__a._M_a) { }
113
 
114
      static constexpr _Head&
115
      _M_head(_Head_base& __b) noexcept { return __b; }
116
 
117
      static constexpr const _Head&
118
      _M_head(const _Head_base& __b) noexcept { return __b; }
119
    };
120
 
121
  template
122
    struct _Head_base<_Idx, _Head, false>
123
    {
124
      constexpr _Head_base()
125
      : _M_head_impl() { }
126
 
127
      constexpr _Head_base(const _Head& __h)
128
      : _M_head_impl(__h) { }
129
 
130
      template
131
               enable_if
132
                                         __uses_alloc_base>::value>::type>
133
        constexpr _Head_base(_UHead&& __h)
134
        : _M_head_impl(std::forward<_UHead>(__h)) { }
135
 
136
      _Head_base(__uses_alloc0)
137
      : _M_head_impl() { }
138
 
139
      template
140
        _Head_base(__uses_alloc1<_Alloc> __a)
141
        : _M_head_impl(allocator_arg, *__a._M_a) { }
142
 
143
      template
144
        _Head_base(__uses_alloc2<_Alloc> __a)
145
        : _M_head_impl(*__a._M_a) { }
146
 
147
      template
148
        _Head_base(__uses_alloc0, _UHead&& __uhead)
149
        : _M_head_impl(std::forward<_UHead>(__uhead)) { }
150
 
151
      template
152
        _Head_base(__uses_alloc1<_Alloc> __a, _UHead&& __uhead)
153
        : _M_head_impl(allocator_arg, *__a._M_a, std::forward<_UHead>(__uhead))
154
        { }
155
 
156
      template
157
        _Head_base(__uses_alloc2<_Alloc> __a, _UHead&& __uhead)
158
        : _M_head_impl(std::forward<_UHead>(__uhead), *__a._M_a) { }
159
 
160
      static constexpr _Head&
161
      _M_head(_Head_base& __b) noexcept { return __b._M_head_impl; }
162
 
163
      static constexpr const _Head&
164
      _M_head(const _Head_base& __b) noexcept { return __b._M_head_impl; }
165
 
166
      _Head _M_head_impl;
167
    };
168
 
169
  /**
170
   * Contains the actual implementation of the @c tuple template, stored
171
   * as a recursive inheritance hierarchy from the first element (most
172
   * derived class) to the last (least derived class). The @c Idx
173
   * parameter gives the 0-based index of the element stored at this
174
   * point in the hierarchy; we use it to implement a constant-time
175
   * get() operation.
176
   */
177
  template
178
    struct _Tuple_impl;
179
 
180
  /**
181
   * Zero-element tuple implementation. This is the basis case for the
182
   * inheritance recursion.
183
   */
184
  template
185
    struct _Tuple_impl<_Idx>
186
    {
187
      template friend class _Tuple_impl;
188
 
189
      _Tuple_impl() = default;
190
 
191
      template
192
        _Tuple_impl(allocator_arg_t, const _Alloc&) { }
193
 
194
      template
195
        _Tuple_impl(allocator_arg_t, const _Alloc&, const _Tuple_impl&) { }
196
 
197
      template
198
        _Tuple_impl(allocator_arg_t, const _Alloc&, _Tuple_impl&&) { }
199
 
200
    protected:
201
      void _M_swap(_Tuple_impl&) noexcept { /* no-op */ }
202
    };
203
 
204
  // Use the Empty Base-class Optimization for empty, non-final types.
205
  template
206
    using __empty_not_final
207
      = typename conditional<__is_final(_Tp), false_type, is_empty<_Tp>>::type;
208
 
209
  /**
210
   * Recursive tuple implementation. Here we store the @c Head element
211
   * and derive from a @c Tuple_impl containing the remaining elements
212
   * (which contains the @c Tail).
213
   */
214
  template
215
    struct _Tuple_impl<_Idx, _Head, _Tail...>
216
    : public _Tuple_impl<_Idx + 1, _Tail...>,
217
      private _Head_base<_Idx, _Head, __empty_not_final<_Head>::value>
218
    {
219
      template friend class _Tuple_impl;
220
 
221
      typedef _Tuple_impl<_Idx + 1, _Tail...> _Inherited;
222
      typedef _Head_base<_Idx, _Head, __empty_not_final<_Head>::value> _Base;
223
 
224
      static constexpr _Head&
225
      _M_head(_Tuple_impl& __t) noexcept { return _Base::_M_head(__t); }
226
 
227
      static constexpr const _Head&
228
      _M_head(const _Tuple_impl& __t) noexcept { return _Base::_M_head(__t); }
229
 
230
      static constexpr _Inherited&
231
      _M_tail(_Tuple_impl& __t) noexcept { return __t; }
232
 
233
      static constexpr const _Inherited&
234
      _M_tail(const _Tuple_impl& __t) noexcept { return __t; }
235
 
236
      constexpr _Tuple_impl()
237
      : _Inherited(), _Base() { }
238
 
239
      explicit
240
      constexpr _Tuple_impl(const _Head& __head, const _Tail&... __tail)
241
      : _Inherited(__tail...), _Base(__head) { }
242
 
243
      template
244
               enable_if::type>
245
        explicit
246
        constexpr _Tuple_impl(_UHead&& __head, _UTail&&... __tail)
247
        : _Inherited(std::forward<_UTail>(__tail)...),
248
          _Base(std::forward<_UHead>(__head)) { }
249
 
250
      constexpr _Tuple_impl(const _Tuple_impl&) = default;
251
 
252
      constexpr
253
      _Tuple_impl(_Tuple_impl&& __in)
254
      noexcept(__and_,
255
                      is_nothrow_move_constructible<_Inherited>>::value)
256
      : _Inherited(std::move(_M_tail(__in))),
257
        _Base(std::forward<_Head>(_M_head(__in))) { }
258
 
259
      template
260
        constexpr _Tuple_impl(const _Tuple_impl<_Idx, _UElements...>& __in)
261
        : _Inherited(_Tuple_impl<_Idx, _UElements...>::_M_tail(__in)),
262
          _Base(_Tuple_impl<_Idx, _UElements...>::_M_head(__in)) { }
263
 
264
      template
265
        constexpr _Tuple_impl(_Tuple_impl<_Idx, _UHead, _UTails...>&& __in)
266
        : _Inherited(std::move
267
                     (_Tuple_impl<_Idx, _UHead, _UTails...>::_M_tail(__in))),
268
          _Base(std::forward<_UHead>
269
                (_Tuple_impl<_Idx, _UHead, _UTails...>::_M_head(__in))) { }
270
 
271
      template
272
        _Tuple_impl(allocator_arg_t __tag, const _Alloc& __a)
273
        : _Inherited(__tag, __a),
274
          _Base(__use_alloc<_Head>(__a)) { }
275
 
276
      template
277
        _Tuple_impl(allocator_arg_t __tag, const _Alloc& __a,
278
                    const _Head& __head, const _Tail&... __tail)
279
        : _Inherited(__tag, __a, __tail...),
280
          _Base(__use_alloc<_Head, _Alloc, _Head>(__a), __head) { }
281
 
282
      template
283
               typename = typename enable_if
284
                                             == sizeof...(_UTail)>::type>
285
        _Tuple_impl(allocator_arg_t __tag, const _Alloc& __a,
286
                    _UHead&& __head, _UTail&&... __tail)
287
        : _Inherited(__tag, __a, std::forward<_UTail>(__tail)...),
288
          _Base(__use_alloc<_Head, _Alloc, _UHead>(__a),
289
                std::forward<_UHead>(__head)) { }
290
 
291
      template
292
        _Tuple_impl(allocator_arg_t __tag, const _Alloc& __a,
293
                    const _Tuple_impl& __in)
294
        : _Inherited(__tag, __a, _M_tail(__in)),
295
          _Base(__use_alloc<_Head, _Alloc, _Head>(__a), _M_head(__in)) { }
296
 
297
      template
298
        _Tuple_impl(allocator_arg_t __tag, const _Alloc& __a,
299
                    _Tuple_impl&& __in)
300
        : _Inherited(__tag, __a, std::move(_M_tail(__in))),
301
          _Base(__use_alloc<_Head, _Alloc, _Head>(__a),
302
                std::forward<_Head>(_M_head(__in))) { }
303
 
304
      template
305
        _Tuple_impl(allocator_arg_t __tag, const _Alloc& __a,
306
                    const _Tuple_impl<_Idx, _UElements...>& __in)
307
        : _Inherited(__tag, __a,
308
                     _Tuple_impl<_Idx, _UElements...>::_M_tail(__in)),
309
          _Base(__use_alloc<_Head, _Alloc, _Head>(__a),
310
                _Tuple_impl<_Idx, _UElements...>::_M_head(__in)) { }
311
 
312
      template
313
        _Tuple_impl(allocator_arg_t __tag, const _Alloc& __a,
314
                    _Tuple_impl<_Idx, _UHead, _UTails...>&& __in)
315
        : _Inherited(__tag, __a, std::move
316
                     (_Tuple_impl<_Idx, _UHead, _UTails...>::_M_tail(__in))),
317
          _Base(__use_alloc<_Head, _Alloc, _UHead>(__a),
318
                std::forward<_UHead>
319
                (_Tuple_impl<_Idx, _UHead, _UTails...>::_M_head(__in))) { }
320
 
321
      _Tuple_impl&
322
      operator=(const _Tuple_impl& __in)
323
      {
324
        _M_head(*this) = _M_head(__in);
325
        _M_tail(*this) = _M_tail(__in);
326
        return *this;
327
      }
328
 
329
      _Tuple_impl&
330
      operator=(_Tuple_impl&& __in)
331
      noexcept(__and_,
332
                      is_nothrow_move_assignable<_Inherited>>::value)
333
      {
334
        _M_head(*this) = std::forward<_Head>(_M_head(__in));
335
        _M_tail(*this) = std::move(_M_tail(__in));
336
        return *this;
337
      }
338
 
339
      template
340
        _Tuple_impl&
341
        operator=(const _Tuple_impl<_Idx, _UElements...>& __in)
342
        {
343
          _M_head(*this) = _Tuple_impl<_Idx, _UElements...>::_M_head(__in);
344
          _M_tail(*this) = _Tuple_impl<_Idx, _UElements...>::_M_tail(__in);
345
          return *this;
346
        }
347
 
348
      template
349
        _Tuple_impl&
350
        operator=(_Tuple_impl<_Idx, _UHead, _UTails...>&& __in)
351
        {
352
          _M_head(*this) = std::forward<_UHead>
353
            (_Tuple_impl<_Idx, _UHead, _UTails...>::_M_head(__in));
354
          _M_tail(*this) = std::move
355
            (_Tuple_impl<_Idx, _UHead, _UTails...>::_M_tail(__in));
356
          return *this;
357
        }
358
 
359
    protected:
360
      void
361
      _M_swap(_Tuple_impl& __in)
362
      noexcept(noexcept(swap(std::declval<_Head&>(),
363
                             std::declval<_Head&>()))
364
               && noexcept(_M_tail(__in)._M_swap(_M_tail(__in))))
365
      {
366
        using std::swap;
367
        swap(_M_head(*this), _M_head(__in));
368
        _Inherited::_M_swap(_M_tail(__in));
369
      }
370
    };
371
 
372
  /// Primary class template, tuple
373
  template
374
    class tuple : public _Tuple_impl<0, _Elements...>
375
    {
376
      typedef _Tuple_impl<0, _Elements...> _Inherited;
377
 
378
    public:
379
      constexpr tuple()
380
      : _Inherited() { }
381
 
382
      explicit
383
      constexpr tuple(const _Elements&... __elements)
384
      : _Inherited(__elements...) { }
385
 
386
      template
387
        enable_if<__and_
388
                                        _Elements>...>::value>::type>
389
        explicit
390
        constexpr tuple(_UElements&&... __elements)
391
        : _Inherited(std::forward<_UElements>(__elements)...) {     }
392
 
393
      constexpr tuple(const tuple&) = default;
394
 
395
      constexpr tuple(tuple&&) = default;
396
 
397
      template
398
        enable_if<__and_
399
                                        _Elements>...>::value>::type>
400
        constexpr tuple(const tuple<_UElements...>& __in)
401
        : _Inherited(static_cast&>(__in))
402
        { }
403
 
404
      template
405
        enable_if<__and_
406
                                        _Elements>...>::value>::type>
407
        constexpr tuple(tuple<_UElements...>&& __in)
408
        : _Inherited(static_cast<_Tuple_impl<0, _UElements...>&&>(__in)) { }
409
 
410
      // Allocator-extended constructors.
411
 
412
      template
413
        tuple(allocator_arg_t __tag, const _Alloc& __a)
414
        : _Inherited(__tag, __a) { }
415
 
416
      template
417
        tuple(allocator_arg_t __tag, const _Alloc& __a,
418
              const _Elements&... __elements)
419
        : _Inherited(__tag, __a, __elements...) { }
420
 
421
      template
422
               enable_if
423
                         == sizeof...(_Elements)>::type>
424
        tuple(allocator_arg_t __tag, const _Alloc& __a,
425
              _UElements&&... __elements)
426
        : _Inherited(__tag, __a, std::forward<_UElements>(__elements)...)
427
        { }
428
 
429
      template
430
        tuple(allocator_arg_t __tag, const _Alloc& __a, const tuple& __in)
431
        : _Inherited(__tag, __a, static_cast(__in)) { }
432
 
433
      template
434
        tuple(allocator_arg_t __tag, const _Alloc& __a, tuple&& __in)
435
        : _Inherited(__tag, __a, static_cast<_Inherited&&>(__in)) { }
436
 
437
      template
438
               enable_if
439
                         == sizeof...(_Elements)>::type>
440
        tuple(allocator_arg_t __tag, const _Alloc& __a,
441
              const tuple<_UElements...>& __in)
442
        : _Inherited(__tag, __a,
443
                     static_cast&>(__in))
444
        { }
445
 
446
      template
447
               enable_if
448
                         == sizeof...(_Elements)>::type>
449
        tuple(allocator_arg_t __tag, const _Alloc& __a,
450
              tuple<_UElements...>&& __in)
451
        : _Inherited(__tag, __a,
452
                     static_cast<_Tuple_impl<0, _UElements...>&&>(__in))
453
        { }
454
 
455
      tuple&
456
      operator=(const tuple& __in)
457
      {
458
        static_cast<_Inherited&>(*this) = __in;
459
        return *this;
460
      }
461
 
462
      tuple&
463
      operator=(tuple&& __in)
464
      noexcept(is_nothrow_move_assignable<_Inherited>::value)
465
      {
466
        static_cast<_Inherited&>(*this) = std::move(__in);
467
        return *this;
468
      }
469
 
470
      template
471
               enable_if
472
                         == sizeof...(_Elements)>::type>
473
        tuple&
474
        operator=(const tuple<_UElements...>& __in)
475
        {
476
          static_cast<_Inherited&>(*this) = __in;
477
          return *this;
478
        }
479
 
480
      template
481
               enable_if
482
                         == sizeof...(_Elements)>::type>
483
        tuple&
484
        operator=(tuple<_UElements...>&& __in)
485
        {
486
          static_cast<_Inherited&>(*this) = std::move(__in);
487
          return *this;
488
        }
489
 
490
      void
491
      swap(tuple& __in)
492
      noexcept(noexcept(__in._M_swap(__in)))
493
      { _Inherited::_M_swap(__in); }
494
    };
495
 
496
  // Explicit specialization, zero-element tuple.
497
  template<>
498
    class tuple<>
499
    {
500
    public:
501
      void swap(tuple&) noexcept { /* no-op */ }
502
    };
503
 
504
  /// Partial specialization, 2-element tuple.
505
  /// Includes construction and assignment from a pair.
506
  template
507
    class tuple<_T1, _T2> : public _Tuple_impl<0, _T1, _T2>
508
    {
509
      typedef _Tuple_impl<0, _T1, _T2> _Inherited;
510
 
511
    public:
512
      constexpr tuple()
513
      : _Inherited() { }
514
 
515
      explicit
516
      constexpr tuple(const _T1& __a1, const _T2& __a2)
517
      : _Inherited(__a1, __a2) { }
518
 
519
      template
520
               enable_if<__and_,
521
                                is_convertible<_U2, _T2>>::value>::type>
522
        explicit
523
        constexpr tuple(_U1&& __a1, _U2&& __a2)
524
        : _Inherited(std::forward<_U1>(__a1), std::forward<_U2>(__a2)) { }
525
 
526
      constexpr tuple(const tuple&) = default;
527
 
528
      constexpr tuple(tuple&&) = default;
529
 
530
      template
531
        enable_if<__and_,
532
                         is_convertible>::value>::type>
533
        constexpr tuple(const tuple<_U1, _U2>& __in)
534
        : _Inherited(static_cast&>(__in)) { }
535
 
536
      template
537
               enable_if<__and_,
538
                                is_convertible<_U2, _T2>>::value>::type>
539
        constexpr tuple(tuple<_U1, _U2>&& __in)
540
        : _Inherited(static_cast<_Tuple_impl<0, _U1, _U2>&&>(__in)) { }
541
 
542
      template
543
        enable_if<__and_,
544
                         is_convertible>::value>::type>
545
        constexpr tuple(const pair<_U1, _U2>& __in)
546
        : _Inherited(__in.first, __in.second) { }
547
 
548
      template
549
               enable_if<__and_,
550
                                is_convertible<_U2, _T2>>::value>::type>
551
        constexpr tuple(pair<_U1, _U2>&& __in)
552
        : _Inherited(std::forward<_U1>(__in.first),
553
                     std::forward<_U2>(__in.second)) { }
554
 
555
      // Allocator-extended constructors.
556
 
557
      template
558
        tuple(allocator_arg_t __tag, const _Alloc& __a)
559
        : _Inherited(__tag, __a) { }
560
 
561
      template
562
        tuple(allocator_arg_t __tag, const _Alloc& __a,
563
              const _T1& __a1, const _T2& __a2)
564
        : _Inherited(__tag, __a, __a1, __a2) { }
565
 
566
      template
567
        tuple(allocator_arg_t __tag, const _Alloc& __a, _U1&& __a1, _U2&& __a2)
568
        : _Inherited(__tag, __a, std::forward<_U1>(__a1),
569
                     std::forward<_U2>(__a2)) { }
570
 
571
      template
572
        tuple(allocator_arg_t __tag, const _Alloc& __a, const tuple& __in)
573
        : _Inherited(__tag, __a, static_cast(__in)) { }
574
 
575
      template
576
        tuple(allocator_arg_t __tag, const _Alloc& __a, tuple&& __in)
577
        : _Inherited(__tag, __a, static_cast<_Inherited&&>(__in)) { }
578
 
579
      template
580
        tuple(allocator_arg_t __tag, const _Alloc& __a,
581
              const tuple<_U1, _U2>& __in)
582
        : _Inherited(__tag, __a,
583
                     static_cast&>(__in))
584
        { }
585
 
586
      template
587
        tuple(allocator_arg_t __tag, const _Alloc& __a, tuple<_U1, _U2>&& __in)
588
        : _Inherited(__tag, __a, static_cast<_Tuple_impl<0, _U1, _U2>&&>(__in))
589
        { }
590
 
591
      template
592
        tuple(allocator_arg_t __tag, const _Alloc& __a,
593
              const pair<_U1, _U2>& __in)
594
        : _Inherited(__tag, __a, __in.first, __in.second) { }
595
 
596
      template
597
        tuple(allocator_arg_t __tag, const _Alloc& __a, pair<_U1, _U2>&& __in)
598
        : _Inherited(__tag, __a, std::forward<_U1>(__in.first),
599
                     std::forward<_U2>(__in.second)) { }
600
 
601
      tuple&
602
      operator=(const tuple& __in)
603
      {
604
        static_cast<_Inherited&>(*this) = __in;
605
        return *this;
606
      }
607
 
608
      tuple&
609
      operator=(tuple&& __in)
610
      noexcept(is_nothrow_move_assignable<_Inherited>::value)
611
      {
612
        static_cast<_Inherited&>(*this) = std::move(__in);
613
        return *this;
614
      }
615
 
616
      template
617
        tuple&
618
        operator=(const tuple<_U1, _U2>& __in)
619
        {
620
          static_cast<_Inherited&>(*this) = __in;
621
          return *this;
622
        }
623
 
624
      template
625
        tuple&
626
        operator=(tuple<_U1, _U2>&& __in)
627
        {
628
          static_cast<_Inherited&>(*this) = std::move(__in);
629
          return *this;
630
        }
631
 
632
      template
633
        tuple&
634
        operator=(const pair<_U1, _U2>& __in)
635
        {
636
          this->_M_head(*this) = __in.first;
637
          this->_M_tail(*this)._M_head(*this) = __in.second;
638
          return *this;
639
        }
640
 
641
      template
642
        tuple&
643
        operator=(pair<_U1, _U2>&& __in)
644
        {
645
          this->_M_head(*this) = std::forward<_U1>(__in.first);
646
          this->_M_tail(*this)._M_head(*this) = std::forward<_U2>(__in.second);
647
          return *this;
648
        }
649
 
650
      void
651
      swap(tuple& __in)
652
      noexcept(noexcept(__in._M_swap(__in)))
653
      { _Inherited::_M_swap(__in); }
654
    };
655
 
656
 
657
  /// Gives the type of the ith element of a given tuple type.
658
  template
659
    struct tuple_element;
660
 
661
  /**
662
   * Recursive case for tuple_element: strip off the first element in
663
   * the tuple and retrieve the (i-1)th element of the remaining tuple.
664
   */
665
  template
666
    struct tuple_element<__i, tuple<_Head, _Tail...> >
667
    : tuple_element<__i - 1, tuple<_Tail...> > { };
668
 
669
  /**
670
   * Basis case for tuple_element: The first element is the one we're seeking.
671
   */
672
  template
673
    struct tuple_element<0, tuple<_Head, _Tail...> >
674
    {
675
      typedef _Head type;
676
    };
677
 
678
  template
679
    struct tuple_element<__i, const _Tp>
680
    {
681
      typedef typename
682
      add_const::type>::type type;
683
    };
684
 
685
  template
686
    struct tuple_element<__i, volatile _Tp>
687
    {
688
      typedef typename
689
      add_volatile::type>::type type;
690
    };
691
 
692
  template
693
    struct tuple_element<__i, const volatile _Tp>
694
    {
695
      typedef typename
696
      add_cv::type>::type type;
697
    };
698
 
699
  /// Finds the size of a given tuple type.
700
  template
701
    struct tuple_size;
702
 
703
  template
704
    struct tuple_size
705
    : public integral_constant<
706
             typename remove_cv::value)>::type,
707
             tuple_size<_Tp>::value> { };
708
 
709
  template
710
    struct tuple_size
711
    : public integral_constant<
712
             typename remove_cv::value)>::type,
713
             tuple_size<_Tp>::value> { };
714
 
715
  template
716
    struct tuple_size
717
    : public integral_constant<
718
             typename remove_cv::value)>::type,
719
             tuple_size<_Tp>::value> { };
720
 
721
  /// class tuple_size
722
  template
723
    struct tuple_size>
724
    : public integral_constant { };
725
 
726
  template
727
    constexpr typename __add_ref<_Head>::type
728
    __get_helper(_Tuple_impl<__i, _Head, _Tail...>& __t) noexcept
729
    { return _Tuple_impl<__i, _Head, _Tail...>::_M_head(__t); }
730
 
731
  template
732
    constexpr typename __add_c_ref<_Head>::type
733
    __get_helper(const _Tuple_impl<__i, _Head, _Tail...>& __t) noexcept
734
    { return _Tuple_impl<__i, _Head, _Tail...>::_M_head(__t); }
735
 
736
  // Return a reference (const reference, rvalue reference) to the ith element
737
  // of a tuple.  Any const or non-const ref elements are returned with their
738
  // original type.
739
  template
740
    constexpr typename __add_ref<
741
                      typename tuple_element<__i, tuple<_Elements...>>::type
742
                    >::type
743
    get(tuple<_Elements...>& __t) noexcept
744
    { return __get_helper<__i>(__t); }
745
 
746
  template
747
    constexpr typename __add_c_ref<
748
                      typename tuple_element<__i, tuple<_Elements...>>::type
749
                    >::type
750
    get(const tuple<_Elements...>& __t) noexcept
751
    { return __get_helper<__i>(__t); }
752
 
753
  template
754
    constexpr typename __add_r_ref<
755
                      typename tuple_element<__i, tuple<_Elements...>>::type
756
                    >::type
757
    get(tuple<_Elements...>&& __t) noexcept
758
    { return std::forward
759
        tuple<_Elements...>>::type&&>(get<__i>(__t)); }
760
 
761
  // This class helps construct the various comparison operations on tuples
762
  template
763
           typename _Tp, typename _Up>
764
    struct __tuple_compare;
765
 
766
  template
767
    struct __tuple_compare<0, __i, __j, _Tp, _Up>
768
    {
769
      static bool
770
      __eq(const _Tp& __t, const _Up& __u)
771
      {
772
        return (get<__i>(__t) == get<__i>(__u) &&
773
                __tuple_compare<0, __i + 1, __j, _Tp, _Up>::__eq(__t, __u));
774
      }
775
 
776
      static bool
777
      __less(const _Tp& __t, const _Up& __u)
778
      {
779
        return ((get<__i>(__t) < get<__i>(__u))
780
                || !(get<__i>(__u) < get<__i>(__t)) &&
781
                __tuple_compare<0, __i + 1, __j, _Tp, _Up>::__less(__t, __u));
782
      }
783
    };
784
 
785
  template
786
    struct __tuple_compare<0, __i, __i, _Tp, _Up>
787
    {
788
      static bool
789
      __eq(const _Tp&, const _Up&) { return true; }
790
 
791
      static bool
792
      __less(const _Tp&, const _Up&) { return false; }
793
    };
794
 
795
  template
796
    bool
797
    operator==(const tuple<_TElements...>& __t,
798
               const tuple<_UElements...>& __u)
799
    {
800
      typedef tuple<_TElements...> _Tp;
801
      typedef tuple<_UElements...> _Up;
802
      return (__tuple_compare::value - tuple_size<_Up>::value,
803
              0, tuple_size<_Tp>::value, _Tp, _Up>::__eq(__t, __u));
804
    }
805
 
806
  template
807
    bool
808
    operator<(const tuple<_TElements...>& __t,
809
              const tuple<_UElements...>& __u)
810
    {
811
      typedef tuple<_TElements...> _Tp;
812
      typedef tuple<_UElements...> _Up;
813
      return (__tuple_compare::value - tuple_size<_Up>::value,
814
              0, tuple_size<_Tp>::value, _Tp, _Up>::__less(__t, __u));
815
    }
816
 
817
  template
818
    inline bool
819
    operator!=(const tuple<_TElements...>& __t,
820
               const tuple<_UElements...>& __u)
821
    { return !(__t == __u); }
822
 
823
  template
824
    inline bool
825
    operator>(const tuple<_TElements...>& __t,
826
              const tuple<_UElements...>& __u)
827
    { return __u < __t; }
828
 
829
  template
830
    inline bool
831
    operator<=(const tuple<_TElements...>& __t,
832
               const tuple<_UElements...>& __u)
833
    { return !(__u < __t); }
834
 
835
  template
836
    inline bool
837
    operator>=(const tuple<_TElements...>& __t,
838
               const tuple<_UElements...>& __u)
839
    { return !(__t < __u); }
840
 
841
  // NB: DR 705.
842
  template
843
    constexpr tuple::__type...>
844
    make_tuple(_Elements&&... __args)
845
    {
846
      typedef tuple::__type...>
847
        __result_type;
848
      return __result_type(std::forward<_Elements>(__args)...);
849
    }
850
 
851
  template
852
    constexpr tuple<_Elements&&...>
853
    forward_as_tuple(_Elements&&... __args) noexcept
854
    { return tuple<_Elements&&...>(std::forward<_Elements>(__args)...); }
855
 
856
 
857
  template struct array;
858
 
859
  template
860
    constexpr _Tp& get(array<_Tp, _Nm>&) noexcept;
861
 
862
  template
863
    constexpr _Tp&& get(array<_Tp, _Nm>&&) noexcept;
864
 
865
  template
866
    constexpr const _Tp& get(const array<_Tp, _Nm>&) noexcept;
867
 
868
  template
869
    struct __is_tuple_like_impl : false_type
870
    { };
871
 
872
  template
873
    struct __is_tuple_like_impl> : true_type
874
    { };
875
 
876
  template
877
    struct __is_tuple_like_impl> : true_type
878
    { };
879
 
880
  template
881
    struct __is_tuple_like_impl> : true_type
882
    { };
883
 
884
  // Internal type trait that allows us to sfinae-protect tuple_cat.
885
  template
886
    struct __is_tuple_like
887
    : public __is_tuple_like_impl
888
            ::type>::type>::type
889
    { };
890
 
891
  // Stores a tuple of indices.  Also used by bind() to extract the elements
892
  // in a tuple.
893
  template
894
    struct _Index_tuple
895
    {
896
      typedef _Index_tuple<_Indexes..., sizeof...(_Indexes)> __next;
897
    };
898
 
899
  // Builds an _Index_tuple<0, 1, 2, ..., _Num-1>.
900
  template
901
    struct _Build_index_tuple
902
    {
903
      typedef typename _Build_index_tuple<_Num - 1>::__type::__next __type;
904
    };
905
 
906
  template<>
907
    struct _Build_index_tuple<0>
908
    {
909
      typedef _Index_tuple<> __type;
910
    };
911
 
912
  template
913
    struct __make_tuple_impl;
914
 
915
  template
916
           std::size_t _Nm>
917
    struct __make_tuple_impl<_Idx, tuple<_Tp...>, _Tuple, _Nm>
918
    {
919
      typedef typename __make_tuple_impl<_Idx + 1, tuple<_Tp...,
920
        typename std::tuple_element<_Idx, _Tuple>::type>, _Tuple, _Nm>::__type
921
      __type;
922
    };
923
 
924
  template
925
    struct __make_tuple_impl<_Nm, tuple<_Tp...>, _Tuple, _Nm>
926
    {
927
      typedef tuple<_Tp...> __type;
928
    };
929
 
930
  template
931
    struct __do_make_tuple
932
    : public __make_tuple_impl<0, tuple<>, _Tuple,
933
                               std::tuple_size<_Tuple>::value>
934
    { };
935
 
936
  // Returns the std::tuple equivalent of a tuple-like type.
937
  template
938
    struct __make_tuple
939
    : public __do_make_tuple
940
            ::type>::type>
941
    { };
942
 
943
  // Combines several std::tuple's into a single one.
944
  template
945
    struct __combine_tuples;
946
 
947
  template<>
948
    struct __combine_tuples<>
949
    {
950
      typedef tuple<> __type;
951
    };
952
 
953
  template
954
    struct __combine_tuples>
955
    {
956
      typedef tuple<_Ts...> __type;
957
    };
958
 
959
  template
960
    struct __combine_tuples, tuple<_T2s...>, _Rem...>
961
    {
962
      typedef typename __combine_tuples,
963
                                        _Rem...>::__type __type;
964
    };
965
 
966
  // Computes the result type of tuple_cat given a set of tuple-like types.
967
  template
968
    struct __tuple_cat_result
969
    {
970
      typedef typename __combine_tuples
971
        ::__type...>::__type __type;
972
    };
973
 
974
  // Helper to determine the index set for the first tuple-like
975
  // type of a given set.
976
  template
977
    struct __make_1st_indices;
978
 
979
  template<>
980
    struct __make_1st_indices<>
981
    {
982
      typedef std::_Index_tuple<> __type;
983
    };
984
 
985
  template
986
    struct __make_1st_indices<_Tp, _Tpls...>
987
    {
988
      typedef typename std::_Build_index_tuple
989
        typename std::remove_reference<_Tp>::type>::value>::__type __type;
990
    };
991
 
992
  // Performs the actual concatenation by step-wise expanding tuple-like
993
  // objects into the elements,  which are finally forwarded into the
994
  // result tuple.
995
  template
996
    struct __tuple_concater;
997
 
998
  template
999
    struct __tuple_concater<_Ret, std::_Index_tuple<_Is...>, _Tp, _Tpls...>
1000
    {
1001
      template
1002
        static constexpr _Ret
1003
        _S_do(_Tp&& __tp, _Tpls&&... __tps, _Us&&... __us)
1004
        {
1005
          typedef typename __make_1st_indices<_Tpls...>::__type __idx;
1006
          typedef __tuple_concater<_Ret, __idx, _Tpls...>      __next;
1007
          return __next::_S_do(std::forward<_Tpls>(__tps)...,
1008
                               std::forward<_Us>(__us)...,
1009
                               std::get<_Is>(std::forward<_Tp>(__tp))...);
1010
        }
1011
    };
1012
 
1013
  template
1014
    struct __tuple_concater<_Ret, std::_Index_tuple<>>
1015
    {
1016
      template
1017
        static constexpr _Ret
1018
        _S_do(_Us&&... __us)
1019
        {
1020
          return _Ret(std::forward<_Us>(__us)...);
1021
        }
1022
    };
1023
 
1024
  template
1025
           enable_if<__and_<__is_tuple_like<_Tpls>...>::value>::type>
1026
    constexpr auto
1027
    tuple_cat(_Tpls&&... __tpls)
1028
    -> typename __tuple_cat_result<_Tpls...>::__type
1029
    {
1030
      typedef typename __tuple_cat_result<_Tpls...>::__type __ret;
1031
      typedef typename __make_1st_indices<_Tpls...>::__type __idx;
1032
      typedef __tuple_concater<__ret, __idx, _Tpls...> __concater;
1033
      return __concater::_S_do(std::forward<_Tpls>(__tpls)...);
1034
    }
1035
 
1036
  template
1037
    inline tuple<_Elements&...>
1038
    tie(_Elements&... __args) noexcept
1039
    { return tuple<_Elements&...>(__args...); }
1040
 
1041
  template
1042
    inline void
1043
    swap(tuple<_Elements...>& __x, tuple<_Elements...>& __y)
1044
    noexcept(noexcept(__x.swap(__y)))
1045
    { __x.swap(__y); }
1046
 
1047
  // A class (and instance) which can be used in 'tie' when an element
1048
  // of a tuple is not required
1049
  struct _Swallow_assign
1050
  {
1051
    template
1052
      const _Swallow_assign&
1053
      operator=(const _Tp&) const
1054
      { return *this; }
1055
  };
1056
 
1057
  const _Swallow_assign ignore{};
1058
 
1059
  /// Partial specialization for tuples
1060
  template
1061
    struct uses_allocator, _Alloc> : true_type { };
1062
 
1063
  // See stl_pair.h...
1064
  template
1065
    template
1066
      inline
1067
      pair<_T1, _T2>::
1068
      pair(piecewise_construct_t,
1069
           tuple<_Args1...> __first, tuple<_Args2...> __second)
1070
      : pair(__first, __second,
1071
             typename _Build_index_tuple::__type(),
1072
             typename _Build_index_tuple::__type())
1073
      { }
1074
 
1075
  template
1076
    template
1077
             typename... _Args2, std::size_t... _Indexes2>
1078
      inline
1079
      pair<_T1, _T2>::
1080
      pair(tuple<_Args1...>& __tuple1, tuple<_Args2...>& __tuple2,
1081
           _Index_tuple<_Indexes1...>, _Index_tuple<_Indexes2...>)
1082
      : first(std::forward<_Args1>(std::get<_Indexes1>(__tuple1))...),
1083
        second(std::forward<_Args2>(std::get<_Indexes2>(__tuple2))...)
1084
      { }
1085
 
1086
_GLIBCXX_END_NAMESPACE_VERSION
1087
} // namespace
1088
 
1089
#endif // __GXX_EXPERIMENTAL_CXX0X__
1090
 
1091
#endif // _GLIBCXX_TUPLE

powered by: WebSVN 2.1.0

© copyright 1999-2024 OpenCores.org, equivalent to Oliscience, all rights reserved. OpenCores®, registered trademark.