zone-alloc
This crate provides data types for zone-based (also known as region-based or arena-based) data allocation. Zone-based allocation is a type of memory management in which allocated objects are assigned to a specific zone. Data in the zone remain valid and usable for the lifetime of the zone, and all data in the zone are deallocated together after use.
[]
= "0.1"
Usage
This crate defines three containers:
Arena<T>- A container that can be used for arena allocation of values of a given type.Registry<T>- An extension ofArena<T>that provides integer handles for allocated data.StrongRegistry<H, T>- An extension ofRegistry<T>that provides strongly-typed handles for allocated data.KeyedArena<K, T>- An extension ofArena<T>that maintains a mapping of keys to values.
Additional Crates
zone-alloc-strong-handle-derive- Procedural macro for deriving theStrongHandleinterface on simple wrappers around theHandletype when working withStrongRegistry.
Features
While the crate is by default built with the Rust standard library, this feature can be removed for no-std environments.
default-std,ahashstd- Depend on the Rust standard library.ahash- Use the ahash library for hash maps.
Examples
Linked List Nodes with Arena<T>
use zone_alloc::Arena;
#[derive(Debug, PartialEq, Eq)]
struct Node<'a, T> {
parent: Option<&'a Node<'a, T>>,
value: T,
}
impl<'a, T> Node<'a, T> {
pub fn new(parent: Option<&'a Node<'a, T>>, value: T) -> Self {
Self { parent, value }
}
}
fn main() {
let arena = Arena::new();
let node = arena.alloc(Node::new(None, 1));
let node = arena.alloc(Node::new(Some(node), 2));
let node = arena.alloc(Node::new(Some(node), 3));
assert_eq!(node.value, 3);
assert_eq!(node.parent.unwrap().value, 2);
assert_eq!(node.parent.unwrap().parent.unwrap().value, 1);
assert_eq!(node.parent.unwrap().parent.unwrap().parent, None);
}
Circular References with Registry<T>
use zone_alloc::{
Handle,
Registry,
};
#[derive(Debug, PartialEq, Eq)]
struct Node<T> {
parent: Option<Handle>,
value: T,
}
impl<T> Node<T> {
pub fn new(parent: Option<Handle>, value: T) -> Self {
Self { parent, value }
}
}
fn main() {
let registry = Registry::new();
let root_handle = registry.register(Node::new(None, "first"));
let handle = registry.register(Node::new(Some(root_handle), "second"));
let handle = registry.register(Node::new(Some(handle), "third"));
registry.get_mut(root_handle).unwrap().parent = Some(handle);
let node = registry.get(handle).unwrap();
assert_eq!(node.value, "third");
let node = registry.get(node.parent.unwrap()).unwrap();
assert_eq!(node.value, "second");
let node = registry.get(node.parent.unwrap()).unwrap();
assert_eq!(node.value, "first");
let node = registry.get(node.parent.unwrap()).unwrap();
assert_eq!(node.value, "third");
}