[C/C++] vector

할랑말랑·2026년 3월 13일

C/C++

목록 보기
23/45

vector

C++ STL에서 제공하는 동적 배열 클래스이다.
배열의 크기를 동적으로 조절할 수 있는 기능을 제공한다.

특징

  • 동적 크기 : 필요한 만큼의 메모리를 할당하고, 요소가 추가되면 자동으로 크기를 조정한다.
    메모리 할당이 필요할 경우, 기존 요소를 새로운 메모리 블록으로 복사한다.
  • 임의 접근 : 벡터의 요소에 인덱스를 통해 빠르게 접근할 수 있다.
  • 메모리 관리 : 벡터는 자동으로 메모리를 관리하므로, 사용자가 직접 메모리 할당 및 해제를 신경 쓸 필요가 없다.
  • 다양한 멤버 함수 : 요소의 추가, 삭제, 크기 조정등 쉽게 수행할 수 있다.

주요 멤버함수

1. 생성자 / 할당 및 초기화

#include <iostream>
#include <vector>

int main()
{
    // 기본 생성자 : 빈 벡터 생성
    std::vector<int> v1;

    // 초기화 리스트로 생성
    std::vector<int> v2 = { 1,2,3,4,5 };

    // std::vector(const T& valye) : 복사 생성자
    std::vector<int> v3 = v2;

    // std::vector(const T&& other) noexcept : 이동 생성자
    std::vector<int> v4 = std::move(v2);

    // 지정된 개수만큼 기본값으로 초기화된 요소를 가진 벡터 객체 생성
    std::vector<int> v5(5);

    // 지정된 개수만큼 value로 초기화된 요소를 가진 벡터 객체 생성
    std::vector<int> v6(5,10);

    // 복사 대입 연산자
    std::vector<int> v7;
    v7 = v6;

    // 이동 대입 연산자
    std::vector<int> v8;
    v8 = std::move(v7);

    // 초기화 리스트 대입
    std::vector<int> v9;
    v9 = { 4,5,6,7,8 };

    // assign(size_t count, const T& value) : 지정된 개수만큼 value로 초기화
    // 반환 타입 : void
    std::vector<int> v10;
    v10.assign(10, 20);
}

2. 접근자

#include <iostream>
#include <vector>

int main()
{
    std::vector<int> vec(10, 10);

    try
    {
        // 지정된 인덱스의 요소 반환(범위 체크)
        auto v = vec.at(20);
    }
    catch (std::out_of_range)
    {
        std::cout << "유효하지 않은 인덱스에 접근" << std::endl;
    }

    // [] 연산자 오버로딩 : 지정된 인덱스의 요소 반환(범위 체크 없음)
    auto v2 = vec[0];

    // 첫 번째 요소 반환
    auto v3 = vec.front();
    // 마지막 요소 반환
    auto v4 = vec.back();
    // 내부 데이터 포인터 반환
    int* v5 = vec.data();
    std::cout << "내부 요소 데이터 포인터 반환 : " << v5 << std::endl;
    std::cout << "첫 번째 요소 : " << v5[0] << std::endl;

    return 0;
}

3. 조작(삽입/삭제)

#include <iostream>
#include <vector>
#include <string>

class Person
{
public:
    std::string name;
    int age;

    Person() : name("Name"), age(20) {};
    Person(std::string _name, int _age) : name(_name), age(_age) {};
};

int main()
{
    std::vector<int> vec(10, 10);

    // push_back(const T& value) : 벡터 끝에 요소 추가
    vec.push_back(300);

    // emplace_back은 새로운 요소를 컨테이너에 추가할 때, 해당 요소를 직접 생성한다(복사 생성자, 이동 생성자 호출 X)
    // 매개변수로 전달된 인자를 사용하여 컨테이너 내부에서 직접 객체를 생성합니다.
    vec.emplace_back(10);

    std::vector<Person> vp;
    vp.push_back(Person("12", 2)); // 기본 이동 생성자로 소유권 이전
    Person p("참치", 100);
    vp.push_back(p);             // 기본 복사 생성자로 값은 복사

    vp.emplace_back("고구마", 600); // 컨테이너 내부 메모리에서 직접 객체 생성

    // insert(iterator pos, const T& value) : 지정된 위치에 요소 삽입
    vec.insert(vec.begin()+1, 2);

    // erase(iterator pos) : 지정된 위치의 요소 삭제
    vec.erase(vec.end()-1);

    // clear() : 모든 요소 삭제
    vec.clear();

    // pop_back() : 마지막 요소 삭제
    vp.pop_back();

    // resize(size_t count) : 벡터의 크기를 count로 조절
    std::cout << "vec size : " << vec.size() << std::endl;
    vec.resize(100);
    std::cout << "vec rsize(100) : " << vec.size() << std::endl;

    return 0;
}

참고

  • push_back() : 이미 생성된 객체를 컨테이너에 추가하고, 자원을 이전할 때 사용
  • emplace_back : 새로운 객체를 생성할 때, 필요한 인자를 직접 전달하여 효율적으로 추가할 때 사용

4. 길이 및 용량

#include <iostream>
#include <vector>

int main()
{
    std::vector<int> vec = { 5,4,20,2 };

    // size() : 현재 벡터의 요소 개수 반환
    std::cout << "vec 크기 : " << vec.size() << std::endl;
    // capacity() : 현재 할당된 메모리 용량 반환
    std::cout << "vec 용량 : " << vec.capacity() << std::endl;
    // empty() : 벡터가 비어있는지 여부 반환 비어있으면 true = 1 아니면 false = 0
    std::cout << "vec 벡터 빈 여부 : " << vec.empty() << std::endl;

    // reserve(size_t new_cap) : 최소한의 새 용량을 예약
    vec.reserve(20);
    std::cout << "vec reserve(20) 용량 : " << vec.capacity() << std::endl;

    return 0;
}

참고

  • size는 벡터의 실제로 저장된 요소의 개수이고 capacity는 벡터가 재할당 없이 저장할 수 있는 요소의 최대 개수이다.

capacity가 꽉 찼을 경우

  • capacity가 꽉 찼을 때는 새로운 메모리를 할당 일반적으로 현재 capacity의 1.5또는 2배 크기로 새로운 메모리를 할당한다
  • 기존 메모리의 모든 요소를 새로운 메모리로 이동/복사 한다.(이동 생성자가 있으면 이동/없으면 복사 생성자)
  • 새 요소 추가
  • 이전 메모리 해제

5. 반복자

#include <iostream>
#include <vector>

int main()
{
    std::vector<int> v1 = { 1,2,3,4,5 };

    // begin() : 첫 번째 요소를 가리키는 반복자 반환
    std::vector<int>::iterator it1 = v1.begin();

    // end() : 마지막 요소의 다음을 가리키는 반복자 반환
    std::vector<int>::iterator it2 = v1.end();

    // rbegin : 역방향 첫 번째 요소를 가리키는 반복자 반환
    std::vector<int>::reverse_iterator it3 = v1.rbegin();

    // rend : 역방향 마지막 요소의 다음을 가리키는 반복자 반환
    std::vector<int>::reverse_iterator it4 = v1.rend();

    // cbegin() : 첫 번째 요소를 가리키는 const 반복자 반환
    std::vector<int>::const_iterator it5 = v1.cbegin();

    // cend() : 마지막 요소의 다음을 가리키는 const 반복자 반환
    std::vector<int>::const_iterator it6 = v1.cend();

    // crbegin : 역방향 첫 번째 요소를 가리키는 const 반복자 반환
    std::vector<int>::const_reverse_iterator it7 = v1.crbegin();

    // crend : 역방향 마지막 요소의 다음을 가리키는 const 반복자 반환
    std::vector<int>::const_reverse_iterator it8 = v1.crend();
}

6. 연산자

#include <iostream>
#include <vector>

int main()
{
    // 벡터 초기화
    std::vector<int> vec = { 5,4,20,2 };
    std::vector<int> vec2(10, 20); // 10개의 요소를 20으로 초기화
    std::vector<int> vec3 = { 5,4,20,2 };
    std::vector<int> vec4 = vec2; // vec2를 복사하여 vec4 생성

    // operator== : 두 벡터의 크기와 모든 요소가 순서대로 일치하는지 비교
    if (vec == vec3)
    {
        std::cout << "벡터가 같다" << std::endl;
    }

    // operator!= : 두 벡터가 다른지 비교 (크기 또는 요소 중 하나라도 다르면 true)
    if (vec != vec2)
    {
        std::cout << "벡터가 다르다" << std::endl;
    }

    // 사전식 순서(lexicographical order)로 비교 : >, >=, <, <=
    // 첫 번째 요소부터 순서대로 비교하여, 처음으로 다른 요소가 나오는 지점에서 대소를 결정합니다.
    if (vec >= vec3) // vec와 vec3는 모든 요소가 같으므로 >=는 true 입니다.
    {
        std::cout << "vec >= vec3" << std::endl;
    }

    if (vec3 < vec2) // vec3의 첫 요소(5)가 vec2의 첫 요소(20)보다 작으므로, vec3 < vec2는 true 입니다.
    {
        std::cout << "vec3 < vec2" << std::endl;
    }

    // --- 벡터 연결 방법 ---

    // 1. 벡터 연결은 insert() 사용
    // vec4의 끝(vec4.end())에 vec의 시작(vec.begin())부터 끝(vec.end())까지의 모든 요소를 삽입합니다.
    vec4.insert(vec4.end(), vec.begin(), vec.end());
    std::cout << "vec4 : ";
    for (const auto& item : vec4)
    {
        std::cout << item << " ";
    }
    std::cout << std::endl;

    // 2. 반복문 사용
    // vec2의 모든 요소를 하나씩 반복하여 vec의 끝에 추가(push_back)합니다.
    for (int val : vec2)
    {
        vec.push_back(val);
    }
    std::cout << "vec : ";
    for (const auto& item : vec)
    {
        std::cout << item << " ";
    }
    std::cout << std::endl;

    return 0;
}

참고

  • C++ 에서 std::vector는 사전식 순서(lexicographical order)로 비교
    표준 std::vector는 operator+와 operator+=를 지원하지 않는다
    벡터를 연결하려면 다른 방법을 사용해야 한다.

7. 기타

  • data() : 내부 요소 데이터 포인터 반환
  • get_allocator()
  • swap(std::vector& other)

0개의 댓글