안녕하세요.
오늘은 컨테이너 타입에 관계없이 특정 범위의 요소를 복사하여 컨테이너의 특정 위치에 추가할 수 있는 copy 함수와 함께 자주 사용되는 반복자 어댑터 back_inserter 함수에 대해 알아보겠습니다.
Header: <algorithm>
template <class InputIterator, class OutputIterator>
OutputIterator copy (InputIterator first, InputIterator last, OutputIterator result);
: [first, last) 범위의 모든 요소를 result가 가리키는 위치부터 순차적으로 복사합니다.
이때, result가 가리키는 위치의 저장 공간은 충분하다고 가정합니다. copy 함수가 공간을 확보해주지 않습니다. 요소 저장은 내부적으로 '=' 연산, 즉 대입을 통해 저장되기 때문에 push_back처럼 자동으로 크기를 늘려주며 요소를 저장하지 않습니다. 따라서 요소를 저장할 수 있는 공간이 없다면 런타임 에러가 발생하게 됩니다. 이 문제의 해결책 중 하나로 잠시 후 살펴볼 back_inserter 함수와 함께 자주 사용합니다. 함수 종료 시 result를 반환합니다.
Header: <iterator>
template <class Container>
back_insert_iterator<Container> back_inserter (Container& x);
: 컨테이너를 받아 back_insert_iterator 타입의 객체를 생성하여 반환합니다.
back_insert_iterator 타입은 일종의 반복자 클래스로, push_back 함수처럼 컨테이너의 끝에 쉽게 삽입을 할 수 있도록 도와줍니다. 해당 타입은 요소를 복사 또는 이동할 목적지를 가리키는 반복자로 사용할 때 용이합니다. 예를 들어 내부적으로 '=' 연산을 사용하여 목적지에 요소를 저장하는 std::copy 또는 std::transform과 같은 함수를 사용할 경우 컨테이너의 잔여 공간을 신경 써줘야 하는 불편함이 있습니다. 즉, 위에서 살펴본 copy의 output 인자로 back_insert_iterator 타입이 아닌 기본 반복자(begin, end)를 사용한다면 잔여 공간이 충분치 않을 경우 런타임 에러가 납니다. 하지만 back_insert_iterator 타입의 객체는 '=' 연산을 통해 요소에 값을 저장하더라도 내부적으로 push_back을 호출하도록 오버 로딩되어 있습니다. 따라서 저장 공간을 프로그래머가 신경 쓸 필요가 없습니다.
back_insert_iterator 클래스와 transform 함수에 대한 더 자세한 내용은
다음 포스팅을 참고해주세요!
2019/11/04 - [C++/Function] - [C++ STL] std::transform() 함수 사용법 / back_insert_iterator
How to work)
copy(begin, end, out);
/*
위 코드는 [begin, end) 범위의 모든 요소를
out이 가리키는 위치부터 순차적으로 복사합니다.
위 코드는 아래 코드와 같은 방식으로 동작합니다.
*/
while(begin != end)
{
*out = *begin;
++out;
++begin;
}
Example)
#include <iostream>
#include <algorithm> // std::copy
#include <iterator> // std::back_inserter
#include <vector>
int main(void)
{
std::vector<int> foo { 1, 2, 3, 4, 5 };
std::vector<int> bar { 10, 20, 30, 40, 50 };
// foo 뒤에 순차적으로 bar의 요소들을 copy합니다.
std::copy(bar.begin(), bar.end(), std::back_inserter(foo));
for (const int val : foo)
{
std::cout << val << " ";
}
std::cout << "\n";
return 0;
}
Explain)
std::copy(bar.begin(), bar.end(), std::back_inserter(foo));
컨테이너 bar의 처음부터 마지막 범위 (=모든) 요소를 컨테이너 foo의 마지막 요소의 다음 위치부터 순차적으로 복사하며 확장합니다.
Output)
참고)
'C,C++ > C++' 카테고리의 다른 글
[C++ STL] 특정 값 제외 컨테이너 복사 std::remove_copy() 함수 (0) | 2019.11.06 |
---|---|
[C++] std::transform() 함수 및 back_inserter 함수에 대해 알아보자 (0) | 2019.11.04 |
[C++] std::equal 함수로 간단하게 회문 판별 함수 구현해보기 / palindrome (0) | 2019.11.02 |
[C++] 공백 단위로 문자열 자르는 split 함수 구현 ( find_if() 사용 ) (0) | 2019.11.01 |
[C++] 수행 시간 측정 clock 함수 | ctime, clock_t, measure time (0) | 2019.10.13 |
댓글