yaml-cpp para C++: guía completa con ejemplos prácticos

Entrenador de Python en Línea para Principiantes

Aprende Python fácilmente sin sobrecargarte de teoría. Resuelve tareas prácticas con verificación automática, recibe pistas y escribe código directamente en el navegador, sin instalar nada.

Start Course

yaml-cpp para C++: guía completa con ejemplos prácticos

1. ¿Qué es y para qué sirve?

yaml-cpp es una biblioteca moderna y ligera de C++ para analizar (parsear) y generar archivos YAML. YAML (YAML Ain't Markup Language) es un formato de serialización de datos fácil de leer para los humanos, muy utilizado en archivos de configuración, descripción de estructuras de datos, pipelines de CI/CD (por ejemplo, GitHub Actions, GitLab CI) y para el intercambio de datos entre servicios. A diferencia de JSON, YAML admite comentarios, cadenas multilínea, anclajes y alias, lo que lo hace ideal para configuraciones.

¿Por qué usar yaml-cpp? Si estás desarrollando una aplicación en C++ que necesita leer archivos de configuración (como ajustes de servidor, parámetros de un modelo de machine learning o descripciones de dependencias), yaml-cpp te ofrece una API sencilla y type-safe. La biblioteca cumple completamente con la especificación YAML 1.2, soporta todos los tipos de datos (escalares, secuencias, mapeos) y permite convertir documentos YAML a estructuras de C++ y viceversa de forma sencilla.

Ventajas clave: dependencias mínimas (solo la biblioteca estándar de C++11/14/17), compilación opcional header-only, soporte para Unicode, serialización personalizada para tipos definidos por el usuario y una comunidad activa (más de 5,000 estrellas en GitHub).

2. Instalación

yaml-cpp no se instala mediante gestores de paquetes de lenguajes como pip o npm. En C++, se usan los gestores de paquetes del sistema o se compila desde el código fuente.

Linux (Debian/Ubuntu)

sudo apt-get install libyaml-cpp-dev

macOS (Homebrew)

brew install yaml-cpp

Windows (vcpkg)

vcpkg install yaml-cpp

Compilación desde el código fuente (CMake)

git clone https://github.com/jbeder/yaml-cpp.git
cd yaml-cpp
mkdir build && cd build
cmake -DYAML_BUILD_SHARED_LIBS=ON ..
make
sudo make install

Después de la instalación, vincula la biblioteca en tu archivo CMakeLists.txt:

find_package(yaml-cpp REQUIRED)
target_link_libraries(mi_proyecto yaml-cpp)

3. Inicio rápido — ejemplo mínimo funcional

Crea un archivo config.yaml:

servidor:
  host: "localhost"
  puerto: 8080
depuracion: true

Ahora, léelo con yaml-cpp:

#include <iostream>
#include <yaml-cpp/yaml.h>

int main() {
    // Cargamos el archivo YAML
    YAML::Node config = YAML::LoadFile("config.yaml");
    
    // Leemos los valores
    std::string host = config["servidor"]["host"].as<std::string>();
    int puerto = config["servidor"]["puerto"].as<int>();
    bool depuracion = config["depuracion"].as<bool>();
    
    std::cout << "Host: " << host << "\n";
    std::cout << "Puerto: " << puerto << "\n";
    std::cout << "Depuración: " << std::boolalpha << depuracion << "\n";
    
    return 0;
}

Compilación: g++ -std=c++17 main.cpp -lyaml-cpp -o app

4. Métodos, funciones y clases principales

4.1. YAML::Node — la clase principal para trabajar con nodos

Firma: class YAML::Node

Descripción: Representa cualquier elemento de un documento YAML: un escalar, una secuencia (arreglo) o un mapeo (diccionario). Soporta iteración, acceso por clave/índice y verificación de tipo.

YAML::Node nodo;
nodo["nombre"] = "Ana";
nodo["edad"] = 30;
nodo["pasatiempos"].push_back("leer");
nodo["pasatiempos"].push_back("programar");

std::cout << nodo["nombre"].as<std::string>() << "\n"; // Ana
std::cout << nodo["pasatiempos"][0].as<std::string>() << "\n"; // leer

4.2. YAML::LoadFile() — carga desde un archivo

Firma: YAML::Node YAML::LoadFile(const std::string& nombre_archivo)

Descripción: Carga y analiza un archivo YAML completo, devolviendo el nodo raíz. Lanza una excepción YAML::BadFile si el archivo no existe o no se puede abrir.

try {
    YAML::Node datos = YAML::LoadFile("datos.yaml");
} catch (const YAML::BadFile& e) {
    std::cerr << "Error al abrir el archivo: " << e.what() << "\n";
}

4.3. YAML::Load() — carga desde una cadena de texto

Firma: YAML::Node YAML::Load(const std::string& cadena)

Descripción: Analiza una cadena de texto con contenido YAML. Útil para pruebas unitarias o cuando los datos provienen de una red.

std::string texto_yaml = "nombre: Carlos\nedad: 25\n";
YAML::Node nodo = YAML::Load(texto_yaml);
std::cout << nodo["nombre"].as<std::string>() << "\n"; // Carlos

4.4. YAML::Emitter — generación de YAML

Firma: class YAML::Emitter

Descripción: Permite construir documentos YAML desde cero en C++ y volcarlos a una cadena o archivo. Soporta formato indentado, comentarios y flujos.

YAML::Emitter emisor;
emisor << YAML::BeginMap;
emisor << YAML::Key << "usuario";
emisor << YAML::Value << "admin";
emisor << YAML::Key << "roles";
emisor << YAML::Value << YAML::BeginSeq;
emisor << "lectura" << "escritura";
emisor << YAML::EndSeq;
emisor << YAML::EndMap;

std::cout << emisor.c_str() << "\n";
// Salida:
// usuario: admin
// roles:
//   - lectura
//   - escritura

4.5. YAML::Node::as<T>() — conversión a tipos de C++

Firma: template<typename T> T as() const

Descripción: Convierte el valor del nodo al tipo especificado. Soporta tipos estándar (int, double, std::string, bool, std::vector, std::map) y tipos personalizados si se define una especialización.

YAML::Node nodo = YAML::Load("[1, 2, 3]");
std::vector<int> numeros = nodo.as<std::vector<int>>();
for (int n : numeros) std::cout << n << " "; // 1 2 3

4.6. YAML::Node::IsScalar(), IsSequence(), IsMap() — verificación de tipo

Firma: bool IsScalar() const; bool IsSequence() const; bool IsMap() const;

Descripción: Permiten verificar el tipo del nodo antes de acceder a sus datos, evitando errores en tiempo de ejecución.

YAML::Node nodo = YAML::Load("clave: valor");
if (nodo.IsMap()) {
    for (auto it = nodo.begin(); it != nodo.end(); ++it) {
        std::cout << it->first.as<std::string>() << ": " << it->second.as<std::string>() << "\n";
    }
}

4.7. YAML::Node::operator[] — acceso por clave o índice

Firma: YAML::Node operator[](const std::string& clave); YAML::Node operator[](std::size_t indice);

Descripción: Accede a un subnodo usando una clave (para mapeos) o un índice (para secuencias). Si la clave o índice no existen, se crea un nodo nulo.

YAML::Node datos;
datos["usuario"] = "Juan";
datos["puntuaciones"].push_back(95);
datos["puntuaciones"].push_back(88);
std::cout << datos["puntuaciones"][1].as<int>() << "\n"; // 88

4.8. YAML::Node::push_back() — agregar elementos a una secuencia

Firma: void push_back(const YAML::Node& valor)

Descripción: Añade un elemento al final de una secuencia. Si el nodo no es una secuencia, se convierte automáticamente en una.

YAML::Node lista;
lista.push_back("rojo");
lista.push_back("verde");
lista.push_back("azul");
std::cout << lista.size() << "\n"; // 3

4.9. YAML::Node::remove() — eliminar elementos

Firma: void remove(const std::string& clave); void remove(std::size_t indice);

Descripción: Elimina un elemento de un mapeo por clave o de una secuencia por índice.

YAML::Node config = YAML::Load("a: 1\nb: 2\nc: 3\n");
config.remove("b");
std::cout << config["b"].IsDefined() << "\n"; // false

4.10. YAML::Node::begin() / end() — iteración

Firma: iterator begin(); iterator end(); const_iterator begin() const; const_iterator end() const;

Descripción: Permiten iterar sobre los elementos de un mapeo (pares clave-valor) o una secuencia (valores individuales).

YAML::Node colores = YAML::Load("[rojo, verde, azul]");
for (auto it = colores.begin(); it != colores.end(); ++it) {
    std::cout << it->as<std::string>() << " ";
}
// rojo verde azul

5. Conclusión

yaml-cpp es una herramienta esencial para cualquier desarrollador de C++ que trabaje con archivos de configuración o intercambio de datos en formato YAML. Su API intuitiva, su cumplimiento con el estándar YAML 1.2 y su facilidad de integración la convierten en la opción preferida frente a otras bibliotecas. Ya sea que estés construyendo un servidor, una herramienta de línea de comandos o una aplicación de escritorio, yaml-cpp te ahorrará tiempo y esfuerzo. ¡Comienza a usarla hoy mismo y simplifica la gestión de configuraciones en tus proyectos!

Recommendations