-
Notifications
You must be signed in to change notification settings - Fork 0
/
Copy pathmystl_iterator_base.hpp
131 lines (111 loc) · 3.63 KB
/
mystl_iterator_base.hpp
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
#ifndef _N_MYSTL_ITERATOR_BASE_H
#define _N_MYSTL_ITERATOR_BASE_H
#include <stddef.h>
namespace numb {
struct Input_iterator_tag {};
struct Output_iterator_tag {};
struct Forward_iterator_tag : public Input_iterator_tag {};
struct Bidirectional_iterator_tag : public Forward_iterator_tag {};
struct Random_access_iterator_tag : public Bidirectional_iterator_tag {};
template <typename _Category, typename _Tp, typename _Distance = ptrdiff_t,
typename _Pointer = _Tp*, typename _Reference = _Tp&>
struct Iterator {
typedef _Category iterator_category;
typedef _Tp value_type;
typedef _Distance difference_type;
typedef _Pointer pointer;
typedef _Reference reference;
};
template <typename _Iter>
struct Iterator_traits {
typedef typename _Iter::iterator_category iterator_category;
typedef typename _Iter::value_type value_type;
typedef typename _Iter::difference_type difference_type;
typedef typename _Iter::pointer pointer;
typedef typename _Iter::reference reference;
};
/// Partial specialization for pointer type
template <typename _Tp>
struct Iterator_traits<_Tp*> {
typedef Random_access_iterator_tag iterator_category;
typedef _Tp value_type;
typedef ptrdiff_t difference_type;
typedef _Tp* pointer;
typedef _Tp& reference;
};
template <typename _Tp>
struct Iterator_traits<const _Tp*> {
typedef Random_access_iterator_tag iterator_category;
typedef _Tp value_type;
typedef ptrdiff_t difference_type;
typedef _Tp* pointer;
typedef _Tp& reference;
};
template <typename _Iter>
inline typename Iterator_traits<_Iter>::iterator_category
_Iterator_category(const _Iter&)
{ return typename Iterator_traits<_Iter>::iterator_category(); }
template <typename _InputIterator>
inline typename Iterator_traits<_InputIterator>::difference_type
_Distance(_InputIterator _first, _InputIterator _last, Input_iterator_tag)
{
typename Iterator_traits<_InputIterator>::difference_type n = 0;
while (_first != _last) {
++_first;
++n;
}
return n;
}
template <typename _RandomAccessIterator>
inline typename Iterator_traits<_RandomAccessIterator>::difference_type
_Distance(_RandomAccessIterator _first, _RandomAccessIterator _last, Random_access_iterator_tag)
{
return _last - _first;
}
template <typename _Iter>
inline typename Iterator_traits<_Iter>::difference_type
Distance(_Iter _first, _Iter _last)
{
return _Distance(_first, _last, _Iterator_category(_first));
}
template <typename _InputIterator, typename _Distance>
inline void _Advance(_InputIterator& _i, _Distance _n, Input_iterator_tag)
{
while(_n--)
++_i;
}
template <typename _BidirectionalIterator, typename _Distance>
inline void _Advance(_BidirectionalIterator& _i, _Distance _n, Bidirectional_iterator_tag)
{
if (_n > 0)
while(_n--)
++_i;
else
while(_n++)
--_i;
}
template <typename _RandomAccessIterator, typename _Distance>
inline void _Advance(_RandomAccessIterator& _i, _Distance _n, Random_access_iterator_tag)
{
_i += _n;
}
template <typename _Iter, typename _Distance>
inline void Advance(_Iter& i, _Distance n)
{
typename Iterator_traits<_Iter>::difference_type d = n;
_Advance(i, d, _Iterator_category(i));
}
template <typename _ForwardIterator>
inline _ForwardIterator Next(_ForwardIterator _x, typename Iterator_traits<_ForwardIterator>::difference_type _n = 1)
{
Advance(_x, _n);
return _x;
}
template <typename _BidirectionalIterator>
inline _BidirectionalIterator Prev(_BidirectionalIterator _x, typename Iterator_traits<_BidirectionalIterator>::difference_type _n = 1)
{
Advance(_x, -_n);
return _x;
}
}
#endif