본문 바로가기

Programing/C/C++

[list 복사] list의 모든 데이터를 다른 list로 복사

list의 모든 데이터를 다른 list로 복사
stl의 list는 시퀀스의 중간에 빈번한 삽입, 삭제가 수행될 때 사용하는 시퀀스 컨테이너이다. 이러한 특징에 맞춰 list를 사용하곤 하는데, 종종 저장된 list의 원소들을 복사해서 사용할 필요가 있을 때가 있다. list의 모든 원소를 복사하는 방법에는 여러가지가 있지만, 다음은 assign 멤버 함수와 알고리즘 함수 copy를 사용하여 복사하는 방법에 대한 설명이다. 결론부터 이야기하자면, 단일 원소 버전인 copy 보다는 범위 버전인 assign 함수가 효율성에서 더 좋으므로 사용이 권고되고 있다.

1. assign 멤버 함수를 사용하는 방법

#include <list>

typedef std::list<int> LIST_ID;

LIST_ID lstSrcID;       // 소스 list
LIST_ID lstDestID;     // 복사할 목적지 list

// lstSrcID는 1~4의 값을 갖는다.
lstSrcID.push_back(1);
lstSrcID.push_back(2);
lstSrcID.push_back(3);
lstSrcID.push_back(4);


//위의 lstSrcID의 내용을 assign 멤버 함수를 사용하여 lstDestID로 복사
lstDestID.assign(lstSrcID.begin(), lstSrcID.end());


// lstDestID의 내용 출력 및 삭제
while( !lstDestID.empty() )
{
    TRACE("%d\n", lstDestID.front());
    lstDestID.erase(lstDestID.begin());
}

2. 알고리즘의 copy 함수를 사용하는 방법

list에 있는 원소를 복사하는 다른 방법으로는 알고리즘 함수 copy 를 이용하는 것이다. copy 에 사용되는 back_inserter 함수는 컨테이너의 끝에 원소를 하나씩 추가하는 기능을 갖고 있는데, 이는 copy 함수 내부에서 루프 처리를 하고 있다는 것을 말한다.

#include <list>
#include <algorithm>
...

// lstSrcID 에 원소 추가

//위의 lstSrcID의 내용을 알고리즘 함수 copy를 사용하여 lstDestID로 복사
std::copy(lstSrcID.begin(), lstSrcID.end(),
std::back_inserter(lstDestID));


// lstDestID의 내용 출력 및 삭제
while( !lstDestID.empty() )
{    
    TRACE("%d\n", lstDestID.front());
    lstDestID.erase(lstDestID.begin());
}

다음은 일반적인 copy 함수의 구현입니다.

template <typename InIt, typename OutIt>
OutIt copy(InIt first, InIt last, OutIt result)
{
    for( ; first != last; ++first, ++result )
        *result = *first;

    return restult;
}

위의 1과 2를 통해 list 원소들을 복사하는 방법에 대해 알아봤다. 물론 또다른 방법으로는 직접 루프를 작성하거나 list의 insert 멤버 함수를 사용하는 방법이 있을 것이다. 하지만 효용성의 측면에서 assign 멤버 함수를 사용하여, 원소를 복사하는 것이 좋다고 하는데, 이는 이중 링크트 리스트인 list의 next, prev 포인터가 계속되는 원소 추가에 대해 불필요한 포인터 세팅을 하지 않도록 하고, 한번의 대입 만으로 각 포인터가 삽입 후의 노드 주소 값을 가지도록 세팅해주기 때문이다.

3. stl 사용시 유의할 점

stl 사용시 잘 확인해야 할 점은 'Effective STL'에 설명된 것 처럼 다음과 같다.
 단일 요소를 단위로 동작하는 멤버 함수보다 요소의 범위를 단위로 동작하는 멤버 함수가 더 낫다 (항목 5, pp.57)
 어설프게 손으로 작성한 루프보다 알고리즘이 낫다 (항목 43, pp.272)
 같은 이름을 가진 것이 있다면 일반 알고리즘 함수보다 멤버 함수가 더 낫다(항목 44, pp.282)


※ 참고자료
 Scott Meyers, Effective STL, 인포북, pp.57, pp.272, pp.282
 Alexandrescu Andrei, Modern C++ Design, 인포북, pp.90, copy 함수


출처 : http://allwiz.egloos.com/2751285