Utility Types

Back

Loading concept...

C++ Utility Types: Your Swiss Army Knife for Data! 🛠️

The Story: A Magical Toolbox

Imagine you have a special toolbox at home. Inside, you keep different containers:

  • A lunchbox that holds exactly TWO items (sandwich + juice)
  • A bigger lunchbox that holds MANY items (sandwich + juice + apple + cookie)
  • A mystery box that MIGHT have something inside… or might be empty
  • A shape-shifter box that can hold ONE thing, but that thing could be different types
  • A magic box that can hold ANYTHING at all!

C++ gives you these exact containers! They’re called Utility Types, and they live in the <utility>, <tuple>, <optional>, <variant>, and <any> headers.


1. pair - The Lunchbox for Two 🥪🧃

What is it?

A pair is like a lunchbox with exactly two compartments. You put one thing in the first slot, and another thing in the second slot.

#include <utility>

// A pair of name and age
std::pair<std::string, int> person;
person.first = "Alice";
person.second = 10;

Real Life Example

Think of a dictionary:

  • Word → Definition
  • “Cat” → “A furry pet”
std::pair<std::string, std::string> entry;
entry.first = "Cat";
entry.second = "A furry pet";

Easy Way to Make Pairs

// Use make_pair - it figures out types!
auto myPair = std::make_pair("Hello", 42);
// myPair.first = "Hello"
// myPair.second = 42

Quick Facts About pair

Part What it means
.first Gets the first item
.second Gets the second item
make_pair() Creates a pair easily

2. tuple - The Bigger Lunchbox 🎒

What is it?

A tuple is like a lunchbox with as many compartments as you want! You can store 2, 3, 5, or even 10 different things.

#include <tuple>

// A tuple with name, age, and height
std::tuple<std::string, int, double> student;
student = std::make_tuple("Bob", 12, 4.5);

Getting Items Out

Use std::get<> with the position number (starting from 0):

std::string name = std::get<0>(student); // "Bob"
int age = std::get<1>(student);          // 12
double height = std::get<2>(student);    // 4.5

Unpacking a Tuple (C++17)

You can open all compartments at once!

auto [name, age, height] = student;
// Now name = "Bob", age = 12, height = 4.5
graph TD A["tuple"] --> B["get&lt;0&gt; = Bob"] A --> C["get&lt;1&gt; = 12"] A --> D["get&lt;2&gt; = 4.5"]

3. optional - The Maybe Box 📦❓

What is it?

Sometimes you want to say “I might have a value, or I might not.”

Imagine asking your friend: “Do you have a pet?”

  • “Yes, a dog!” → Has a value
  • “No pets” → No value (but that’s okay!)
#include <optional>

std::optional<std::string> getPet(bool hasPet) {
    if (hasPet) {
        return "Dog";  // Has value!
    }
    return std::nullopt;  // Empty box
}

Checking if There’s Something Inside

std::optional<int> maybeNumber = 42;

if (maybeNumber.has_value()) {
    std::cout << "Got: " << *maybeNumber;
}

// Or use value_or for a backup
int num = maybeNumber.value_or(0);

Why Use optional?

Before optional (dangerous!):

// Using -1 to mean "no value" is confusing!
int findAge(std::string name) {
    if (notFound) return -1;  // Yuck!
    return age;
}

With optional (clear!):

std::optional<int> findAge(std::string n) {
    if (notFound) return std::nullopt;
    return age;  // Crystal clear!
}

4. variant - The Shape-Shifter Box 🔄

What is it?

A variant can hold ONE value, but that value can be different types. Think of a toy that transforms!

#include <variant>

// Can hold int OR string OR double
std::variant<int, std::string, double> data;

data = 42;           // Now holds int
data = "Hello";      // Now holds string
data = 3.14;         // Now holds double

Getting the Value Out

Use std::get<> with the type:

data = "Hello";
std::string s = std::get<std::string>(data);

Safe Way: Check First!

if (std::holds_alternative<int>(data)) {
    int num = std::get<int>(data);
}

Using visit - The Smart Way

std::visit([](auto& val) {
    std::cout << val << "\n";
}, data);
graph TD A["variant"] --> B{What type?} B -->|int| C["Get as int"] B -->|string| D["Get as string"] B -->|double| E["Get as double"]

Why variant Beats union

Old union New variant
Forgets what’s inside Knows the type
Dangerous Type-safe
Manual tracking Automatic

5. any - The Magic Box ✨

What is it?

An any is a magic container that can hold absolutely ANYTHING. It’s like a box that can resize itself for any object!

#include <any>

std::any box;

box = 42;            // Put an int
box = "Hello";       // Now a string
box = 3.14159;       // Now a double
box = std::vector<int>{1,2,3};  // Even this!

Getting Values Out

You must tell it what type you expect:

box = 42;
int num = std::any_cast<int>(box);  // Works!

// Wrong type throws exception!
// std::string s = std::any_cast<std::string>(box);

Check Before You Cast

if (box.has_value()) {
    if (box.type() == typeid(int)) {
        int n = std::any_cast<int>(box);
    }
}

When to Use any

  • When you truly don’t know the type ahead of time
  • For plugin systems
  • For generic storage

Warning: any is slower than variant. Use variant when you know the possible types!


Comparison Chart: Which Container to Use?

Situation Use This
Exactly 2 values pair
Fixed number of values tuple
Maybe has value, maybe not optional
One value, but could be different types variant
Could be literally anything any

Summary: Your New Superpowers!

graph TD A["Utility Types"] --> B["pair - Two items"] A --> C["tuple - Many items"] A --> D["optional - Maybe item"] A --> E["variant - One of several types"] A --> F["any - Anything at all"]

Quick Code Reference

// pair
auto p = std::make_pair("key", 100);

// tuple
auto t = std::make_tuple(1, "two", 3.0);
auto val = std::get<1>(t);

// optional
std::optional<int> opt = 42;
int x = opt.value_or(0);

// variant
std::variant<int, std::string> v = "Hi";
std::string s = std::get<std::string>(v);

// any
std::any a = 3.14;
double d = std::any_cast<double>(a);

You Did It! 🎉

Now you have five powerful containers in your C++ toolbox:

  1. pair - Perfect for key-value pairs
  2. tuple - When you need more than two
  3. optional - Clear “maybe” values
  4. variant - Type-safe alternatives
  5. any - Ultimate flexibility

Go build amazing things with your new tools!

Loading story...

Story - Premium Content

Please sign in to view this story and start learning.

Upgrade to Premium to unlock full access to all stories.

Stay Tuned!

Story is coming soon.

Story Preview

Story - Premium Content

Please sign in to view this concept and start learning.

Upgrade to Premium to unlock full access to all content.