zig-tipos-datos-primitivos

Tipos de datos primitivos en Zig: enteros, flotantes y bool

  • 5 min

Los tipos primitivos en Zig son los bloques básicos con los que representamos números, booleanos y otros valores simples. Si vienes de JavaScript o Python, quizá estés acostumbrado a que un número sea simplemente un Number o un int; en Zig importa cuántos bits ocupa.

Zig es un lenguaje de sistemas, así que el tamaño forma parte del tipo.

En Zig, no decimos “quiero un número”. Decimos: “Quiero un número entero, sin signo, que ocupe exactamente 8 bits”. Esta precisión nos permite:

  1. Ahorrar memoria: no usar 64 bits para guardar un valor que va del 0 al 10.
  2. Comunicar límites: si usas un tipo de 8 bits, el lector sabe que ese valor no puede superar 255.
  3. Evitar errores: el compilador impide asignar una constante que no cabe en el tipo elegido.

Enteros

La sintaxis de los enteros en Zig es maravillosamente lógica. Se compone de una letra (i o u) seguida del número de bits.

  • i (signed integer): enteros con signo, que pueden ser negativos.
  • u (unsigned integer): enteros sin signo, desde cero en adelante.

Los tipos más comunes

Tipo ZigEquivalente C/C++Rango aproximadoUso común
u8unsigned char0 a 255Bytes crudos, píxeles, caracteres ASCII.
i32int-2 mil millones a +2 mil millonesContadores generales, matemáticas estándar.
u64unsigned long long0 a 18 trillonesTamaños de archivos, IDs únicos, timestamps.
i8signed char-128 a 127Números muy pequeños con signo.
const vidas: u8 = 3;           // Correcto, cabe en 8 bits
const temperatura: i8 = -15;   // Correcto, acepta negativos
const saldo: i32 = 100000;     // Correcto
Copied!

Si intentas asignar un valor que no cabe (ej: const a: u8 = 300;), Zig te dará un error de compilación. No hay desbordamientos accidentales al asignar constantes.

isize y usize: el tamaño del puntero

Hay dos tipos especiales cuyo tamaño depende de la arquitectura del procesador (32-bit o 64-bit) donde se ejecute el programa:

  • usize: Un entero sin signo del tamaño de una dirección de memoria.
  • isize: Un entero con signo del mismo tamaño.

En un ordenador moderno (64-bit), usize equivale a u64. ¿Cuándo usamos usize? Es el tipo habitual para índices, longitudes y tamaños en memoria, porque puede representar cualquier posición del espacio de direcciones del proceso.

const array = [_]u8{1, 2, 3};
// Usamos usize para representar el índice.
const indice: usize = 1; 
const valor = array[indice];
Copied!

Enteros de tamaño arbitrario

A diferencia de C, que ofrece un conjunto reducido de anchuras habituales, Zig permite indicar directamente el número de bits de un entero.

¿Necesitas una variable que solo guarde valores del 0 al 3? Puedes usar 2 bits. ¿Estás programando un protocolo de red extraño que usa campos de 7 bits?

const color_3_bits: u3 = 7;   // Máximo valor posible es 7 (111 en binario)
const flags: u7 = 120;        // Un entero de 7 bits
const mascara: u128 = @as(u128, 1) << 100; // Un bit situado en la posición 100
Copied!

Esto resulta útil para bit packing (empaquetado de bits) en sistemas embebidos, protocolos y controladores.

Números de coma flotante

Para números con decimales, Zig sigue el estándar IEEE-754. Aquí no hay distinción de signo (u o i), siempre son f.

  • f32: precisión simple (equivalente habitual a float en C). Es frecuente en gráficos 3D y juegos.
  • f64: doble precisión (equivalente habitual a double en C). Se usa cuando necesitamos más precisión o rango.
  • f16 y f128: tipos menos comunes; su rendimiento y soporte dependen del objetivo.
const pi: f64 = 3.14159265359;
const gravedad: f32 = 9.81;
Copied!

No uses coma flotante para representar importes que deban ser exactos: valores como 0.1 no tienen una representación binaria exacta. Para dinero suele ser preferible guardar la unidad mínima en un entero. Además, para mezclar enteros y flotantes en tiempo de ejecución tendrás que convertirlos explícitamente.

Booleanos

El tipo bool en Zig es estricto. Solo puede valer true o false.

A diferencia de C o JavaScript, los números no son booleanos.

// JavaScript (válido)
// if (1) { ... }

// Zig (ERROR)
// if (1) { ... } -> error: expected type 'bool', found 'comptime_int'
Copied!

Debemos ser explícitos con la condición:

const cantidad = 5;
if (cantidad > 0) { // Esto devuelve true, así que es válido
    std.debug.print("Hay cantidad", .{});
}
Copied!

Esta regla evita confundir una condición booleana con un número o un puntero.

Literales numéricos

Zig nos ofrece algunas comodidades sintácticas para escribir números grandes:

Podemos usar guiones bajos _ para separar miles y hacer el número legible. El compilador los ignora.

const un_millon: i32 = 1_000_000;
const bytes_hex: u16 = 0xFF_AA;
const binario: u8 = 0b1111_0000;
Copied!