ホームに戻る
出典 :
実践C++入門講座 第31回目 イテレータの仕組みと範囲ベースforの仕組み | Theolizer Technology
関連 :
コンテナ ベクトル(動的配列) マップ(連想配列) 型推論
目次 :

イテレータ(反復子)とは

コンテナ(配列を含む)の各要素に対する繰り返し処理を抽象化したもの。
コンテナの各要素への参照(「参照型」とは異なる)を表し、加算すれば次の要素、減算すれば前の要素を指す。
配列(の要素)を指すポインタもイテレータである。
(実際、C++においては、イテレータはポインタと互換性を有するよう設計されている)
独自(ユーザ定義)のクラスに関しても、イテレータを作成することができる。詳細は割愛。

基本型

コンテナの走査は以下のように書ける。ここで、end() イテレータが末尾要素 の次 を指すことに注意。
画像

for() 文はC++11以降であれば、 auto(型推論) を用いて以下のように書ける。
for( auto it = aVector.begin(); it != aVector.end(); ++it )
また、end() が周回ごとに呼ばれるのを避ける( end() に重い処理を含む場合など)には、以下のようにする。
auto end = aVector.end(); for( auto it = aVector.begin(); it != end ; ++it )

イテレータとポインタの違い

vector 、array 、およびC互換の配列は各要素が添字順にメモリに格納されるため、先頭要素へのポインタを加算することで要素を順に走査できる。
しかしそれ以外のコンテナでは、メモリへの格納順がコンテナにおける序列と必ずしも一致せず、ポインタを使用して順に走査することはできない。
イテレータを使用すれば、確実に序列通りに走査できる。

基本的なイテレータ

逆イテレータを使用すれば逆順に走査できる。また要素を参照するのみで更新しないのであれば、読み取り専用イテレータを使用すれば安全。
名前 説明 備考
begin()先頭の要素を指すイテレータを取得する
end()末尾の次を指すイテレータを取得する
cbegin()先頭の要素を指す読み取り専用イテレータを取得する C++11以降
cend()末尾の次を指す読み取り専用イテレータを取得する C++11以降
rbegin()末尾を指す逆イテレータを取得する
rend()先頭の前を指す逆イテレータを取得する
crbegin()末尾を指す読み取り専用逆イテレータを取得する C++11以降
crend()先頭の前を指す読み取り専用逆イテレータを取得する C++11以降

付記

イテレータのインクリメント・デクリメントの際、前置表記( ++it , --it )と後置表記( it++ , it-- )では結果は当然等しいが、
多くの場合(極わずかではあるが) 前置表記のほうが計算負荷が低い。
これは後置表記が、一度コピーを生成した後、コピーを変更して返す(≒リード・モディファイ・ライト)実装となっているため。
但し、2023年現在のCPUの実装では後置表記のほうが速いという説もある。