Appendix D. Important Standard Library APIs

Zig’s standard library is imported with:

Appendix D. Important Standard Library APIs

Zig’s standard library is imported with:

const std = @import("std");

Most useful standard library APIs live under std.

This appendix is a beginner map. It does not cover every function. It shows the parts you will use most often.

D.1 Printing

Use std.debug.print for simple output while learning.

const std = @import("std");

pub fn main() void {
    std.debug.print("Hello\n", .{});
}

With values:

std.debug.print("x = {}\n", .{x});

With strings:

std.debug.print("name = {s}\n", .{name});

Common format patterns:

Pattern Meaning
{} Default formatting
{s} String formatting
{any} Debug-style formatting

D.2 Testing

Use std.testing for unit tests.

const std = @import("std");

fn add(a: i32, b: i32) i32 {
    return a + b;
}

test "add works" {
    try std.testing.expect(add(2, 3) == 5);
}

Run:

zig test main.zig

Useful testing APIs:

API Use
std.testing.expect Assert that a condition is true
std.testing.expectEqual Compare expected and actual values
std.testing.expectError Check that an error happens
std.testing.allocator Allocator for tests

D.3 Memory Allocation

Zig does not hide heap allocation. Many APIs ask for an allocator.

Common allocator type:

std.mem.Allocator

Page allocator:

const allocator = std.heap.page_allocator;

General-purpose allocator pattern:

var gpa = std.heap.GeneralPurposeAllocator(.{}){};
defer _ = gpa.deinit();

const allocator = gpa.allocator();

Arena allocator pattern:

var arena = std.heap.ArenaAllocator.init(std.heap.page_allocator);
defer arena.deinit();

const allocator = arena.allocator();

Allocate bytes:

const buf = try allocator.alloc(u8, 1024);
defer allocator.free(buf);

Important APIs:

API Use
allocator.alloc(T, n) Allocate n items of type T
allocator.free(slice) Free allocated slice
allocator.create(T) Allocate one item
allocator.destroy(ptr) Free one item
std.heap.page_allocator Simple allocator backed by OS pages
std.heap.GeneralPurposeAllocator Debug-friendly general allocator
std.heap.ArenaAllocator Many allocations, one cleanup

D.4 Memory Utilities

std.mem contains functions for working with slices, bytes, and memory.

Compare slices:

if (std.mem.eql(u8, a, b)) {
    // same bytes
}

Copy bytes:

@memcpy(dest, source);

Fill bytes:

@memset(buffer, 0);

Find value:

const index = std.mem.indexOf(u8, text, "needle");

Useful APIs:

API Use
std.mem.eql Compare slices
std.mem.indexOf Find subslice
std.mem.startsWith Check prefix
std.mem.endsWith Check suffix
std.mem.trim Trim characters
std.mem.splitScalar Split by one byte
std.mem.tokenizeScalar Tokenize by one byte

D.5 ArrayList

std.ArrayList is a growable array.

var list = std.ArrayList(i32).init(allocator);
defer list.deinit();

try list.append(10);
try list.append(20);

Access items:

for (list.items) |item| {
    std.debug.print("{}\n", .{item});
}

Useful APIs:

API Use
append Add one item
appendSlice Add many items
pop Remove last item
clearRetainingCapacity Clear but keep memory
clearAndFree Clear and free memory
items Slice of stored items

D.6 Hash Maps

String keys:

var map = std.StringHashMap(i32).init(allocator);
defer map.deinit();

try map.put("one", 1);
try map.put("two", 2);

Get a value:

if (map.get("one")) |value| {
    std.debug.print("{}\n", .{value});
}

Generic hash map:

std.AutoHashMap(K, V)

Useful APIs:

API Use
put Insert or replace
get Read value
contains Check key
remove Remove key
iterator Iterate entries
count Number of entries

D.7 Files

Open a file:

const file = try std.fs.cwd().openFile("data.txt", .{});
defer file.close();

Create a file:

const file = try std.fs.cwd().createFile("out.txt", .{});
defer file.close();

Read and write APIs vary by Zig version. In Zig 0.16, newer I/O APIs use the std.Io model. The main idea remains the same: open files through std.fs, then read or write through the appropriate reader or writer API.

Directory APIs:

API Use
std.fs.cwd() Current working directory
openFile Open existing file
createFile Create or truncate file
makeDir Create directory
deleteFile Delete file
openDir Open directory
close Close file or directory handle

D.8 Paths

Use std.fs.path for path operations.

const base = std.fs.path.basename("/tmp/file.txt");

Useful APIs:

API Use
basename Last path component
dirname Parent path
extension File extension
join Join path parts
isAbsolute Check absolute path

Path handling is platform-sensitive. Avoid manual string concatenation for paths.

D.9 Formatting

Use std.fmt for converting values to text.

Format into a buffer:

var buf: [64]u8 = undefined;

const text = try std.fmt.bufPrint(&buf, "x = {}", .{x});

Parse integer:

const n = try std.fmt.parseInt(i32, "123", 10);

Parse float:

const f = try std.fmt.parseFloat(f64, "3.14");

Useful APIs:

API Use
bufPrint Format into fixed buffer
allocPrint Format into allocated string
parseInt Parse integer
parseFloat Parse float
format Custom formatting support

D.10 Math

Use std.math.

const x = std.math.sqrt(16.0);

Common APIs:

API Use
sqrt Square root
sin, cos, tan Trigonometry
log, log2, log10 Logarithms
min, max Minimum and maximum
clamp Clamp value into range
absInt Absolute value for integers

Some operations may return errors or require specific types. Read the function signature.

D.11 Random Numbers

Use std.Random.

A common pattern:

var prng = std.Random.DefaultPrng.init(12345);
const random = prng.random();

const n = random.int(u32);

For serious security-sensitive randomness, use a cryptographic random source, not a deterministic PRNG.

Useful APIs:

API Use
random.int(T) Random integer
random.float(T) Random float
random.boolean() Random bool
random.bytes(buf) Fill buffer with random bytes

D.12 Time

Use std.time.

const start = std.time.nanoTimestamp();

// work

const end = std.time.nanoTimestamp();
const elapsed = end - start;

Useful APIs:

API Use
nanoTimestamp Current timestamp in nanoseconds
milliTimestamp Current timestamp in milliseconds
sleep Sleep for a duration
ns_per_s Nanoseconds per second
ms_per_s Milliseconds per second

D.13 Process

Use std.process for process-level data and child processes.

Common needs:

API area Use
Arguments Read command-line arguments
Environment Read environment variables
Child process Run another program
Exit code Control process result

In Zig 0.16, process arguments and environment handling are less global and fit better with explicit I/O design. Expect examples to pass context more explicitly than older Zig code.

D.14 Sorting

Use std.sort.

Example idea:

std.sort.heap(i32, items, {}, lessThan);

Comparator:

fn lessThan(_: void, a: i32, b: i32) bool {
    return a < b;
}

Sorting APIs may vary by version, so check the exact signature for your Zig release.

D.15 JSON

Use std.json.

Common operations:

Task API area
Parse JSON std.json.parseFromSlice
Build JSON text std.json.stringify
Read dynamic JSON std.json.Value
Parse into struct typed parsing APIs

Example type:

const User = struct {
    name: []const u8,
    age: u32,
};

JSON APIs often need an allocator because parsed data may allocate memory.

D.16 HTTP

Zig’s standard library includes HTTP support, but HTTP APIs have changed across releases.

For beginner projects, learn these ideas first:

Concept Meaning
Client Sends HTTP requests
Server Receives HTTP requests
Headers Metadata such as content type
Body Request or response data
Method GET, POST, PUT, etc.
Status Response code such as 200 or 404

When using Zig 0.16, prefer examples written for Zig 0.16 because older HTTP examples may not compile unchanged.

D.17 Logging

Use std.log.

std.log.info("server started on port {}", .{port});

Levels:

Level Use
debug Detailed debugging
info Normal information
warn Suspicious but recoverable situation
err Error condition

D.18 Threading

Use std.Thread.

Example shape:

const thread = try std.Thread.spawn(.{}, worker, .{});
thread.join();

Worker:

fn worker() void {
    // work here
}

Related APIs:

API Use
std.Thread.spawn Start a thread
join Wait for thread
std.Thread.Mutex Mutual exclusion
std.Thread.Condition Wait and signal
std.atomic Atomic operations

D.19 Networking

Use std.net for networking.

Common concepts:

Concept Meaning
Address IP address plus port
TCP Reliable byte stream
UDP Datagram protocol
Listener Waits for incoming connections
Stream Read/write connection

Networking code usually involves I/O, errors, buffers, and careful resource cleanup.

D.20 Build System

The build system uses build.zig.

Common names:

API Use
std.Build Build system root type
addExecutable Add executable target
addTest Add test target
addRunArtifact Run a build artifact
standardTargetOptions Target selection
standardOptimizeOption Debug/release mode

A small build script creates an executable, sets its root source file, and installs it.

D.21 C Interop

Zig can import C headers:

const c = @cImport({
    @cInclude("stdio.h");
});

Then call C functions:

_ = c.printf("hello\n");

Zig can also compile C code through:

zig cc

This is one of Zig’s practical strengths.

D.22 Common Import Map

Import Use
std.debug Debug printing
std.testing Tests
std.mem Memory and slice utilities
std.heap Allocators
std.fs Filesystem
std.fs.path Path handling
std.fmt Formatting and parsing
std.math Math helpers
std.time Time
std.process Process APIs
std.json JSON
std.log Logging
std.Thread Threads
std.net Networking
std.Build Build system

D.23 How to Read Standard Library Code

The standard library is ordinary Zig code.

When documentation is unclear, open the source.

Look for:

What to check Why it matters
Function signature Shows arguments, errors, and return type
Allocator parameter Means the function may allocate
Error union Means the function can fail
comptime parameter Means value is known at compile time
defer usage Shows cleanup rules
Tests Show intended behavior

A useful habit is to read signatures before reading implementation.

Example:

pub fn parseInt(comptime T: type, buf: []const u8, radix: u8) !T

This tells you a lot:

T is known at compile time.

buf is the input text.

radix is the base, such as 10 or 16.

The function may fail.

The successful result has type T.

D.24 What to Memorize First

For beginners, memorize these first:

API Why
@import("std") Every Zig file uses it often
std.debug.print Basic output
std.testing.expect Basic tests
std.mem.eql Compare strings and slices
std.heap.page_allocator Simple allocation
std.ArrayList Growable arrays
std.StringHashMap String-key maps
std.fs.cwd() File operations
std.fmt.parseInt Parse numbers
defer with close or free Cleanup

Do not try to memorize the whole standard library. Learn it by solving small problems.