1. 반복자의 종류
- 입력 반복자 : 전방향 읽기(istream)
*iter // 읽기
-> // 멤버 읽기
++ // 전방향 이동
==,!= // 비교
iterator(iter) // 반복자
- 출력 반복자 : 전방향 쓰기(ostream)
*iter = x // 쓰기
++ // 전방향 이동
iterator(iter)(복사생성지) // 반복자
- 순방향 반복자 : 전방향 읽기 + 전방향 쓰기
// 기존 연산자
*iter, ->, ++, ==, !=, iterator(iter)
// 추가된 것
= // 대입
iterator()(기본 생성자) // 반복자
- 양방향 반복자 : 순방향 반복자 + 역방향 읽기 + 역방향 쓰기 (list, set, multiset, map, multimap)
-- // 역방향 이동
- 임의 접근 반복자 : 양방향 반복자 + 랜덤 읽기 + 랜덤 쓰기 (vector, deque)
[], +=, -=, +, -, <, >, <=, >=
※ 순차열 : 순서있는 원소의 집합 // 구간 : 시작과 끝을 나타내는 반복자의 쌍
vector<int> v = {1,2,3,4,5};
// 구간 [b,e), 순차열 : 1,2,3,4,5
2. 반복자와 상수
- X::iterator, X::const_iterator
vector<int>::iterator iter = v.begin(); // 읽기/쓰기 가능
cout << *iter << endl; // 읽기
*iter = 1; // 쓰기
vector<int>::const_iterator citer = v.begin(); // 읽기만 가능
cout << *citer << endl; // 읽기
// *iter = 1; // 불가능함!
- const X::iterator, const X::const_iterator
const vector<int>::iterator const_iter = v.begin(); // 반복자 변경 불가능
// ++const_iter; // 반복자 변경은 불가능함.
const_iterator const_citer = v.begin(); // 읽기만 가능
// *const_citer = 1; // 불가능함
// ++const_citer; // 반복자 변경은 불가능함.
- 정리
반복자 | 쓰기(읽기는 모두 가능) | 반복자 변경 가능 |
X::iterator | O | O |
X::const_iterator | X | O |
const X::iterator | O | X |
const X::const_iteartor | X | X |
3. X::reverse_iterator, X::const_reverse_iterator
모두 역방향 반복자의 형식으로, const에 따라 읽기/쓰기 여부가 정해진다.
vector<int> v = {1,2,3};
for(vector<int>::reverse_iterator riter = v.rbegin(); v != r.rend(); ++iter)
{
cout << *riter << endl;
}
// 정방향 순차열 : 1,2,3
// 정방향 시작점 : 1
// 정방향 마지막 : N
// 역방향 순차열 : 3,2,1
// 역방향 시작점 : 3 (N이 아님)
// 역방향 자미막 : ? (1보다 왼족)
정방향과 역방향의 순차열을 동일하게 만들기 위해 한칸씩 땡겼다. 만약 정방향 반복자를 그대로 사용하고 싶다면?
reverse_iterator<vector<int>>::iteartor rbiter(v.end());
reverse_iterator<vector<int>>::iteartor reiter(v.begin());
4. 삽입 반복자
순차열에 원소를 넣을 수 있게 하는 반복자 어댑터이다.
덮어쓰기가 아닌 삽입이기 때문에 원소의 개수가 늘어난다.
명칭 | 생성되는 객체 | 사용하는 멤버 함수 | 사용 가능한 컨테이너 |
inserter() | insert_iterator | insert() | 모든 컨테이너 |
back_inserter() | back_insert_iterator | push_back() | vector, deque, list : 시퀀스 |
front_inserter() | front_insert_iterator | push_front() | deque, list |
vector<int> v = {1,2,3,4,5};
vector<int> v2;
// copy(b1, e1, insert<T>(v2, b2)) // 덮어쓰기 모드
copy(v1.begin(), v1.end(), insert<vector<int>>(v2, v2.begin());
list<int> lt; // 10->100
list<int> lt2; // 10->100
copy(v.begin(), v.end(), back_insert<list<int>>(lt1));
copy(v.begin(), v.end(), front_insert<list<int>>(lt2));
// back(lt1) : N->10->100->1->2->3->4->5->N
// front(lt2) : N->5->4->3->2->1->10->100->N
5. 입/출력 스트림 반복자
- istream_iterator<T> : 입력 스트림과 연결, T 형식의 값을 스트림에서 읽을 수 있다.
vector<int>;
// 표준 입력 스트림에서 정수를 받는다, 그리고 v에 저장한다.
copy(istream_iterator<int>(cin, istream_iterator<int>(), back_iterator<int>(v));
- ostream_iterator<T> : 출력 스트림과 연결, T 형식의 값을 스트림에서 쓸 수 있다.
vector<int> v = {1,2,3,4,5};
copy<v.begin(), v.end(), ostream_iterator<int>(cout));
// 12345
copy<v.begin(), v.end(), ostream_iteartor<int>(cout, ", ");
// 1, 2, 3, 4, 5,
list<int> lt; // 10, 20, 30
// 화면에 표시(lt와 v, 끝에는 ", "를 붙이고, 두개의 합을)
transform(lt.begin(), lt.end(), v.begin(), v.end(), ostream_iterator<int>(cout, ", "), plus<int>());
// 11, 22, 33, 44, 55
6. 반복자 특성과 보조 함수
반복자는 입력, 출력, 순방향, 양방향, 임의 접근 반복자가 있다.
각 반복자는 자신만의 특징을 가지고, 특징을 저장한 템플릿 클래스를 반복자의 특성이라고 부른다.
advance()와 distance() 함수로 모든 컨테이너가 (+=, -=, +, -) 연산도 가능하게 할 수 있다.
- advance(p,n) : p += n 이동
vector<int> v = {1,2,3};
list<int> lt; // 1, 2, 3
vector<int>::iterator viter(v.begin());
list<int>>iterator riter(lt.begin());
advance(viter, 2); // viter += 2
advance(riter, 2); // riter += 2
cout << *viter << ", " << *riter << endl;
// 2, 2
- n = distance(p1, p2) : n = p2 - p1
list<int> lt; // 1, 2, 3
cout << distance(lt.begin(), lt.end()) << endl; // 원소의 개수 3
// distance의 반환값 : 대부분 unsigned_int, int이지만 반복자에 따라 달라진다.
// difference_type으로 생각하자.
iterator_traits<list<int>::iterator>::differencetype n = distance(lt.begin(), lt.end());
- iterator_traits의 타입
template<class 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 ;
};
'C++ STL > Part 02 STL 이해' 카테고리의 다른 글
12장. string 컨테이너 (0) | 2021.06.22 |
---|---|
11장. 컨테이너 어댑터 (0) | 2021.06.22 |
9장 STL 함수 객체 (0) | 2021.06.22 |
8장 알고리즘 (0) | 2021.06.22 |
7장 연관 컨테이너 (0) | 2021.06.22 |
댓글