-
Notifications
You must be signed in to change notification settings - Fork 16
/
iterator.txt
174 lines (162 loc) · 9.97 KB
/
iterator.txt
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
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
ITERATOR
HEADER ==> #<iterator>
ITERATEURS ==> #Un itérateur est un objet permettant de parcourir un
#container/array.
#Il y a plusieurs manières pour créer un itérateur :
# 1) Via un TYPE d'itérateur, initialisé ou
# défaut-constructed.
# Exemple :
# - CONTAINER<>::iterator ITERATOR;
# - CONTAINER<>::iterator ITERATOR
# ( CONTAINER.begin() )
# - back_insert_interator ITERATOR
# ( back_inserter( ... ) )
# 2) via un adaptor, prenant un autre iterator comme
# argument.
# Exemple : reverse_iterator ITERATOR( ITERATOR2 )
#On peut aussi créer son propre itérateur, qui doit
#donc :
# - implémenter les méthodes supposées par son concept
# - implémenter tous les iterator_traits<...>
#Préférer boost::iterator
ITERATORS, #Les algorithmes utilisant des iterators :
ITERATORS_TRAITS # - checkent leur concepts
ET METHODES ==> # - utilise iterator_traits<...>
# - utilise iterator_category comme un tag pour
# appeler les fonctions appropriées
#Cf Concepts pour les méthodes à implémenter
#pour InputIterator, OutputIterator, etc.
iterator <MOT, WVAR1 #Classe de base : son seul but est d'être héritée par
[, WVAR2[, WVAR3 #une autre classe afin de permettre d'instantier des
[, WVAR4]]]> #iterator_traits plus facilement (voir ci-dessus).
#A faire hériter donc par une classe d'itérateur.
#MOT est une des catégories :
# - input_iterator_tag
# - output_iterator_tag
# - forward_iterator_tag
# - bidirectional_iterator_tag
# - random_access_iterator_tag
#WVAR1 est le type ou la classe manipulée par le
#container/array ciblé.
#WVAR2 est le type utilisé pour calculer la distance
#entre deux positions de l'itérateur, par défaut
#ptrdiff_t
#WVAR3 est le type utilisé pour les pointeurs aux
#éléments du container/array, par défaut WVAR1*
#WVAR4 est le type utilisé pour les références aux
#éléments du container/array, par défaut WVAR1&
#Cette classe ne possède que des membres statiques,
#accessibles donc seulement sans instantiation
#d'iterator, mais dépendant tout de même du template
#donné.
#Ils renvoient des types : la seule manière de les
#utiliser (comme il ne s'agit pas de strings ni de
#nombres) est de mettre iterator<...>::CLASSFK() comme
#argument d'une fonction, et par exemple
#"input_iterator_tag" comme TYPE (sans mettre de VAR,
#inutile) d'un argument dans la déclaration de la
#fonction.
iterator<...>::
value_type() #Renvoie la valeur de WVAR1
iterator<...>::
difference_type() #Renvoie la valeur de WVAR2
iterator<...>::
pointer() #Renvoie la valeur de WVAR3
iterator<...>::
reference() #Renvoie la valeur de WVAR4
iterator<...>::
iterator_category() #Renvoie la valeur de MOT
#Ces membres existent aussi sous la forme de CLASSDT,
#qui sont des types :
iterator<...>::
value_type #Valeur de WVAR1
iterator<...>::
difference_type #Valeur de WVAR2
iterator<...>::
pointer #Valeur de WVAR3
iterator<...>::
reference #Valeur de WVAR4
iterator<...>::
iterator_category #Valeur de MOT
iterator_traits #Struct utilisé pour les traits d'un interator (voir
<ITERATOR> #plus haut. Possède les même membres statiques que
#ITERATOR (fait juste un typedef).
iterator_traits #TYPE* peut par exemple être "int*" ou "CLASS*", etc.
<TYPE*> #Définit les mêmes 10 membres statiques, mais de cette
#manière :
# - value_type : TYPE
# - difference_type : ptrdiff_t
# - pointer : TYPE*
# - reference : TYPE&
# - iterator_category : random_access_iterator_tag
#Ainsi, il est possible de passer un pointeur (d'une
#array dynamique) comme un itérateur en argument d'une
#fonction prenant des itérateurs comme arguments.
reverse_iterator #Renvoie une classe ITERATOR (et non un objet
<ITERATOR> #ITERATOR_VAR) mais reverse, ce qui siginifie que les
#opérations avec des + engendront en fait des -, et
#inversement.
#ITERATOR garde son concept, mais doit être au minimum
#BIDIRECTIONAL.
#Opérations concernées : ++, --, +, -, +=, -= et [] (car
#utilisant implicitement un +)
#A initialisé ensuite avec par exemple CONTTT.rbegin()
#ou CONTTT.rend()
insert_iterator #Classe d'OUTPUT_ITERATOR liée à CONTAINER, mais insert,
<CONTAINER> #ce qui siginifie que :
# - il s'agit d'un output_iterator
# - l'iterator cible toujours le même élément (il est
# donc replacé à cette endroit après chaque output)
# - les éléments sont insérés, non écrasés
# - ++ n'a aucun effet
back_insert_interator #Comme insert_iterator, sauf que :
<CONTAINER> # - l'iterator cible toujours l'élément qui suit le
# dernier élémént ( = mode append), et non le même
# élément.
# - CONTAINER doit cibler une classe qui possède la
# CLASSFK push_back, telle que vector, deque et
# list. Exemple :
# - vector<WVAR>
# Il s'agit d'une classe de container, pas un
# CONTAINER_VAR.
front_insert_interator #Comme insert_iterator, sauf que :
<CONTAINER> # - l'iterator cible toujours l'élément qui précède le
# premier élémént ( = mode append, mais inversé)
# - CONTAINER doit cibler une classe qui possède la
# CLASSFK push_front, telle que deque et list.
INSERT_ITVR(CNTAINR_VAR)#Instantie un INSERT_ITVR, lié à CONTAINER_VAR.
#Le constructor sans argument n'est pas disponible.
INSERT_ITVR(INSRT_ITVR2)#Copy constructor. INSERT_ITVR2 provient souvent d'un
#inserter().
BACK_INSERT_ITVR
(CONTAINER_VAR)
BACK_INSERT_ITVR
(BACK_INSERT_ITVR2) #Comme précédemment, mais pour back_insert_interator
FRONT_INSERT_ITVR
(CONTAINER_VAR)
FRONT_INSERT_ITVR
(FRONT_INSERT_ITVR2) #Comme précédemment, mais pour front_insert_interator
back_inserter(CONTAINER #
_VAR) #Renvoie un BACK_INSERT_ITVR lié à CONTAINER_VAR.
front_inserter(CONTAINR #
_VAR) #Renvoie un FRONT_INSERT_ITVR lié à CONTAINER_VAR.
inserter(CONTAINER_VAR, #Renvoie un INSERT_ITVR lié à CONTAINER_VAR, et placé à
ITERATOR_VAR) #sa position ITVR (ITERATOR_VAR doit donc lui aussi être
#lié à CONTAINER_VAR).
advance(INPT_ITRATR_VAR,#Si INPUT_ITERATOR_VAR est random_access, équivaut à :
SIZE_T_VAL) # - INPUT_ITERATOR_VAR = INPUT_ITERTOR_VAR + SIZE_T_VAL
#Sinon, une succession de ++ ou de -- est effectuée
#SIZE_T_VAL peut être négatif seulement si
#INPUT_ITERATOR_VAR est au moins bidirectional.
distance #Renvoie la différence entre INPUT_ITERATOR_VAR1 (début)
(INPUT_ITERATOR_VAR1, #et INPUT_ITERATOR_VAR2 (fin), sous forme de
INPUT_ITERATOR_VAR2) #iterator_traits<ITERATOR>::difference_type (où ITERATOR
#est la classe des INPUT_ITERATOR_VAR.
#Soit, s'il s'agit de rando_access ITERATOR :
# - INPUT_ITERATOR_VAR2 - INPUT_ITERATOR_VAR1
#Sinon, cela est calculé via une succession de ++ ou de
#-- jusqu'à ce que la distance soit calculée.
#INPUT_ITERATOR_VAR2 ne peut précéder INPUT_ITERATR_VAR1
#que s'ils sont au moins bidirectional.