To serialize and deserialize variables of an enum class type using cereal, you can follow these steps:
Step 1: Include the necessary cereal headers:
#include <cereal/archives/binary.hpp>
#include <cereal/types/utility.hpp>
Step 2: Define your enum class:
enum class State : std::uint8_t {
Idle,
Walking,
Running,
Jumping
};
Step 3: Provide a serialization function for your enum class:
template <class Archive>
void serialize(Archive& ar, State& state) {
std::uint8_t value = static_cast<
std::uint8_t>(state);
ar(value);
state = static_cast<State>(value);
}
This function converts the enum class to its underlying type (std::uint8_t
in this case) for serialization and deserialization.
Step 4: Use the serialize
 function when serializing and deserializing objects that contain the enum class:
class Player {
public:
// ...
private:
friend class cereal::access;
std::string name;
State state;
template <class Archive>
void serialize(Archive& ar) {
ar(name);
// Use the serialization function for State
::serialize(ar, state);
}
};
Note the use of the scope resolution operator ::
to differentiate the serialize
function for PlayerState
from the member function serialize
of the Player
 class.
Step 5: Serialize and deserialize objects containing the enum class as usual:
#include <fstream>
int main() {
// Serialization
Player player("Alice", PlayerState::Running);
std::ofstream outputFile("player.dat");
cereal::BinaryOutputArchive outputArchive(
outputFile);
outputArchive(player);
// Deserialization
Player deserializedPlayer;
std::ifstream inputFile("player.dat");
cereal::BinaryInputArchive inputArchive(
inputFile);
inputArchive(deserializedPlayer);
}
By providing a serialization function for your enum class and using it when serializing and deserializing objects containing the enum class, cereal will be able to handle the serialization and deserialization of enum class variables correctly.
A complete example is available here:
#include <cereal/archives/binary.hpp>
#include <cereal/types/utility.hpp>
#include <cereal/types/string.hpp>
#include <fstream>
#include <iostream>
enum class State : std::uint8_t {
Idle, Walking, Running, Jumping };
template <class Archive>
void serialize(Archive& ar, State& state) {
std::uint8_t value = static_cast<
std::uint8_t>(state);
ar(value);
state = static_cast<State>(value);
}
class Player {
public:
Player() = default;
Player(const std::string& name, State state)
: name(name), state(state) {}
std::string name;
State state;
private:
friend class cereal::access;
template <class Archive>
void serialize(Archive& ar) {
ar(name);
::serialize(ar, state);
}
};
int main() {
// Serialization
Player player("Alice", State::Running);
{
std::ofstream outputFile("player.dat");
cereal::BinaryOutputArchive outputArchive(
outputFile);
outputArchive(player);
}
// Deserialization
Player loadedPlayer;
{
std::ifstream inputFile("player.dat");
cereal::BinaryInputArchive inputArchive(
inputFile);
inputArchive(loadedPlayer);
}
std::cout << "Deserialized Player:\n";
std::cout << "Name: "
<< loadedPlayer.name << "\n";
if (loadedPlayer.state == State::Running) {
std::cout << "State: Running";
}
}
Deserialized Player:
Name: Alice
State: Running
Answers to questions are automatically generated and may not have been reviewed.
A detailed and practical tutorial for binary serialization in modern C++ using the cereal
library.