C++ Alternatives

The following structures are described in A Tour of C++ (second edition) as alternatives where they could be specified to store one or set of alternatives types. There are variant, optional and any imported from standard libraries <variant>, <optional> and <any> respectively which are available in C++17.

variant

A variant could be defined and used as follows:

std::variant<int, bool> x;
// ...
auto y = std::get<bool>(x);

From above, x could hold either an int or a bool value, which closely resembles a union but safer. To get the value from a variant, we can use std::get with a template parameter that specified which type should be retrieved.

optional

An optional could be defined as follows:

std::optional<int> x = 12; // x contains 12
std::optional<int> y = {}; // y is empty

It can either hold a value or be empty by initialise it as {}. In convention, optional should be treated as a pointer to the object rather as an object. This means that x as defined above should be understood as a pointer to an int value which its value is 12. Additionally, * operator on optional to get the value of the variable and the fact that {} is basically the equivalent to nullptr should be able to convince programmers to treat them as so.

Note: Accessing an optional that does not hold a value will result in undefined behaviour, thus renders it as type unsafe.

any

An any could be defined and used as follows:

std::string str = "Hello World!";
std::any message = str;
// ...
std::string recipient = std::any_cast<string>(message);

It could hold any type of value and be later cast by the function std::any_cast. That being said, any can only hold one type of value throughout its lifetime until either it is out of scope or it has called make_any to allocate another any to itself.

#cpp