Skip to content
Laviyx Learn

Try

C++ course menu

The C++ Standard Template Library (STL): Containers, Iterators and Algorithms

An overview of the C++ STL: the three building blocks (containers, iterators, algorithms), sequence vs associative vs unordered containers, container adaptors, how to choose the right container, and Big-O costs of common operations.

Intermediate6 min readUpdated
On this page

The Standard Template Library (STL) is the part of the C++ standard library that provides ready-made containers (data structures) and algorithms (operations on them). It is fast, well tested, and available with every compiler. Knowing it well is one of the most valuable C++ skills: most problems become a few lines once you pick the right container and algorithm.

Three building blocks#

  1. Containers store elements: std::vector, std::map, std::unordered_set, …
  2. Iterators point at elements inside a container and move between them, like generalized pointers.
  3. Algorithms such as std::sort, std::find and std::count_if work on any range described by a pair of iterators.

Because algorithms talk to containers only through iterators, one std::sort works for vectors, arrays and deques alike:

C++
#include <algorithm>
#include <array>
#include <iostream>
#include <vector>

int main() {
    std::vector<int> v = {5, 2, 9, 1};
    std::array<int, 4> a = {8, 3, 7, 4};

    std::sort(v.begin(), v.end());
    std::sort(a.begin(), a.end());

    for (int x : v) std::cout << x << ' ';
    std::cout << "| ";
    for (int x : a) std::cout << x << ' ';
    std::cout << '\n';
}
Output
1 2 5 9 | 3 4 7 8

The containers#

Sequence containers#

Elements are kept in the order you insert them.

ContainerDescription
std::vectorGrowable array. Fast at the end, fast indexing. The default choice.
std::arrayFixed-size array.
std::dequeDouble-ended queue: fast insert/remove at both ends, indexable.
std::listDoubly linked list: fast insert/remove anywhere you hold an iterator, no indexing.
std::stringA sequence of characters.

Associative containers (sorted)#

Elements are kept sorted by key, implemented as balanced binary trees.

ContainerDescription
std::setUnique sorted values
std::mapUnique sorted keys, each with a value
std::multiset / std::multimapLike set/map, but keys may repeat

Unordered containers (hash tables)#

Elements are stored by hash, with no particular order, for very fast average lookups.

ContainerDescription
std::unordered_setUnique values
std::unordered_mapUnique keys with values

Container adaptors#

These wrap another container to provide a restricted interface.

AdaptorDescription
std::stackLast in, first out (LIFO)
std::queueFirst in, first out (FIFO)
std::priority_queueAlways gives the largest (or smallest) element first

Choosing a container#

Ask what you will do most often:

You need to…Use
Store a list and loop over itstd::vector
Look up values by a keystd::unordered_map (or std::map if you need keys in order)
Check "have I seen this?"std::unordered_set (or std::set for sorted output)
Process items in arrival orderstd::queue
Undo history, matching bracketsstd::stack
Always take the most urgent itemstd::priority_queue
Add/remove at both endsstd::deque

When unsure, start with std::vector. Its elements sit next to each other in memory, which modern processors read extremely fast; it often beats "theoretically better" containers for small and medium sizes.

Costs of common operations#

"Big-O" notation describes how the cost grows with the number of elements n:

Operationvectordequelistset / mapunordered_set / unordered_map
Access by indexO(1)O(1)–––
Find a value / keyO(n)O(n)O(n)O(log n)O(1) average
Insert/remove at endO(1)*O(1)O(1)––
Insert/remove at frontO(n)O(1)O(1)––
Insert/remove by key–––O(log n)O(1) average

* amortized: an occasional insert triggers a reallocation, but the average cost stays constant.

A taste of what the STL does for you#

Counting word frequencies, sorted by word, takes a few lines with a std::map:

C++
#include <iostream>
#include <map>
#include <sstream>
#include <string>

int main() {
    std::string text = "the cat and the hat and the bat";
    std::map<std::string, int> counts;

    std::istringstream words(text);
    std::string word;
    while (words >> word) {
        ++counts[word];
    }

    for (const auto& [w, n] : counts) {
        std::cout << w << ": " << n << '\n';
    }
}
Output
and: 2
bat: 1
cat: 1
hat: 1
the: 3

counts[word] creates the entry with value 0 the first time a word appears, then ++ increments it.

Where to go next#

Key takeaway#

Finished this lesson?