rust / expert
Snippet
Implementing a Fixed-Size Circular Queue with Const Generics
This snippet implements a fixed-size ring buffer using Rust's const generics and array types. By asserting the Default trait on the array [Option<T>; N], the buffer can initialize its storage safely without requiring T to be Copy, utilizing atomic-like index wrapping arithmetic.
snippet.rs
rust
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
pub struct ArrayBuffer<T, const N: usize> {data: [Option<T>; N],head: usize,tail: usize,}impl<T, const N: usize> ArrayBuffer<T, N> {pub fn new() -> Selfwhere[Option<T>; N]: Default,{Self {data: Default::default(),head: 0,tail: 0,}}pub fn push(&mut self, item: T) -> Result<(), &'static str> {let next_head = (self.head + 1) % N;if next_head == self.tail {return Err("Queue full");}self.data[self.head] = Some(item);self.head = next_head;Ok(())}}
Breakdown
1
pub struct ArrayBuffer<T, const N: usize>
Declares a generic struct parameterized by both a type T and a const array size N.
2
where [Option<T>; N]: Default
Enforces that the array structure itself can be initialized with default values (which are None).
3
let next_head = (self.head + 1) % N;
Calculates the next write position using modulo arithmetic based on the array size N.
4
self.data[self.head] = Some(item);
Inserts the element into the array slot, taking advantage of standard array indexing.