CodeMIRAI
0 XP

std::vector

3 min read 6 runnable examples Quiz included

A C++ array has a fixed size. std::vector is an array that grows and shrinks as you need, keeps track of its own size, and frees its memory when it goes out of scope. It's the container you'll reach for first.

Adding and reading elements

C++
#include <iostream>
#include <vector>
using namespace std;

int main() {
    vector<int> scores;                // an empty vector of ints
    scores.push_back(82);
    scores.push_back(95);
    scores.push_back(77);
    cout << "size: " << scores.size() << endl;
    cout << "first: " << scores[0] << ", last: " << scores.back() << endl;
    for (int s : scores) cout << s << " ";
    cout << endl;
    return 0;
}
Output
size: 3
first: 82, last: 77
82 95 77 
std::vector<int> v; v.push_back(...) five timessize 1, capacity 1size 2, capacity 2size 3, capacity 4size 5, capacity 8when it's full, the vector moves to a bigger block (usually about double)
size() is how many elements there are; capacity() is how many fit before the next move. reserve() can set it up front.
  • vector<int> says what the vector holds; any type works: vector<string>, vector<double>, even vectors of your own classes.
  • push_back adds to the end, and the vector makes room by itself.
  • size() counts the elements; front() and back() are the first and last.

at() checks, [] doesn't

C++
#include <iostream>
#include <stdexcept>
#include <string>
#include <vector>
using namespace std;

int main() {
    vector<string> names = {"Asha", "Leo", "Mei"};
    cout << names.at(1) << endl;
    try {
        cout << names.at(5) << endl;
    } catch (const out_of_range& e) {
        cout << "Index 5 is out of range" << endl;
    }
    return 0;
}
Output
Leo
Index 5 is out of range

A vector can start with values in braces. names[5] on a three-element vector reads memory that isn't part of it: undefined behaviour, which might print rubbish or crash. at(5) checks the index and throws an out_of_range exception you can catch. Use at while learning, and whenever an index comes from outside your code.

Vectors and functions

C++
#include <iostream>
#include <vector>
using namespace std;

double average(const vector<double>& v) {       // const&: read without copying
    if (v.empty()) return 0;
    double sum = 0;
    for (double x : v) sum += x;
    return sum / v.size();
}

void addBonus(vector<double>& v, double bonus) {  // &: change the caller's vector
    for (double& x : v) x += bonus;
}

int main() {
    vector<double> marks = {72, 88.5, 64, 91};
    cout << average(marks) << endl;
    addBonus(marks, 5);
    cout << average(marks) << endl;
    for (double m : marks) cout << m << " ";
    cout << endl;
    return 0;
}
Output
78.875
83.875
77 93.5 69 96 

Pass a vector by const& to read it and by & to change it. Passing it by value would copy every element on each call.

Inserting and removing

C++
#include <iostream>
#include <vector>
using namespace std;

int main() {
    vector<int> v = {10, 20, 30, 40, 50};
    v.erase(v.begin() + 1);        // remove the element at index 1
    v.insert(v.begin(), 5);        // put 5 at the front
    v.pop_back();                  // drop the last element
    for (int x : v) cout << x << " ";
    cout << endl;
    cout << (v.empty() ? "empty" : "not empty") << ", size " << v.size() << endl;
    v.clear();
    cout << "after clear: " << v.size() << endl;
    return 0;
}
Output
5 10 30 40 
not empty, size 4
after clear: 0

v.begin() is an iterator, a position in the vector; v.begin() + 1 is the second element. Adding or removing at the end is fast. In the middle, every later element must shift along, so that's slower for long vectors.

Reading until the input ends

This example's input is 4 8 15 16 23 42:

C++
#include <iostream>
#include <vector>
using namespace std;

int main() {
    vector<int> nums;
    int x;
    while (cin >> x) nums.push_back(x);      // stops when there's no more input

    int largest = nums[0];
    for (int n : nums) if (n > largest) largest = n;
    cout << "Read " << nums.size() << " numbers. The largest is " << largest << "." << endl;
    return 0;
}
Output
Read 6 numbers. The largest is 42.

cin >> x is false once the input runs out, so the loop reads however many numbers there are. A vector is the natural place to keep them.

A grid: vectors of vectors

C++
#include <iomanip>
#include <iostream>
#include <vector>
using namespace std;

int main() {
    int rows = 3, cols = 4;
    vector<vector<int>> grid(rows, vector<int>(cols, 0));   // 3 rows of 4 zeros
    for (int r = 0; r < rows; r++)
        for (int c = 0; c < cols; c++)
            grid[r][c] = r * cols + c;

    for (const auto& row : grid) {
        for (int x : row) cout << setw(4) << x;
        cout << endl;
    }
    return 0;
}
Output
   0   1   2   3
   4   5   6   7
   8   9  10  11

vector<int>(cols, 0) makes a row of cols zeros, and the outer vector holds rows copies of it. grid[r][c] then works like a 2D array, except the sizes can be chosen while the program runs.

Finished this lesson?Mark it complete to earn +20 XP and move your progress on.