# Pointers

> Single-item pointers that are never null.

A `*T` refers to exactly one `T`. Take an address with `&`, and dereference
with `.*`, a postfix operator, so it chains left to right like field access.

```zig
const std = @import("std");
const expect = std.testing.expect;

fn increment(num: *u8) void {
    num.* += 1;
}

test "take an address and dereference" {
    var x: u8 = 1;
    increment(&x);
    try expect(x == 2);
}

test "pointers to const are const" {
    const x: u8 = 1;
    // `&x` here is a `*const u8`; assigning through it would not compile.
    const ptr: *const u8 = &x;
    try expect(ptr.* == 1);
}

test "pointers are never null" {
    // There is no null `*T`. Absence is spelled `?*T`, and costs nothing
    // extra because the null address is used as the tag.
    var x: u8 = 5;
    const ptr: *u8 = &x;
    const maybe: ?*u8 = ptr;
    try expect(maybe != null);
    try expect(@sizeOf(?*u8) == @sizeOf(*u8));
}
```

*Runnable: compiled to WebAssembly and executed by CI against Zig master. (`02-language.pointers`)*

## Never null

There is no null `*T`. If a pointer may be absent, its type says so: `?*T`.
This is not merely a convention: the compiler will not let you dereference the
optional without unwrapping it first.

The representation costs nothing. Zig uses the null address as the `null` tag,
so `?*T` is the same size as `*T`. You get the safety without the wrapper.

## Constness travels with the pointer

`&some_const` gives you a `*const T`, and you cannot assign through it. Note
that this is about what the *pointer* permits, which is separate from whether
the pointer variable itself can be reassigned:

```zig
var p: *const u8 = &a;   // p can point elsewhere; p.* cannot be written
const q: *u8 = &b;       // q always points at b; q.* can be written
```
