A Stack with Box
The simplest list that compiles, and why Option<Box<T>> is the shape.
pub struct List<T> {
head: Option<Box<Node<T>>>,
}
struct Node<T> {
elem: T,
next: Option<Box<Node<T>>>,
}
Box<T> is a pointer to the heap that owns its contents. It’s what makes a recursive type
finite: Node is one T plus one pointer, regardless of how long the list is.
Option provides the “no next node” case at zero extra cost — the compiler represents
Option<Box<T>> as a nullable pointer, so the enum tag is free.
Push and pop both need Option::take:
pub fn push(&mut self, elem: T) {
let node = Box::new(Node { elem, next: self.head.take() });
self.head = Some(node);
}
take() swaps the value out and leaves None behind. You need it because you can’t move
self.head out of a &mut self — that would leave the struct in a half-initialized state,
which Rust forbids.