Skip to content

Instantly share code, notes, and snippets.

@timClicks
Created June 27, 2023 23:30
Show Gist options
  • Save timClicks/68955827abfe0ff964ce1a61996afed9 to your computer and use it in GitHub Desktop.
Save timClicks/68955827abfe0ff964ce1a61996afed9 to your computer and use it in GitHub Desktop.
Ring buffer implementation
// code from https://youtu.be/TQVwv_e_rMw
#[derive(Debug)]
struct RingBuffer<T: Clone> {
storage: Vec<Option<T>>,
read_idx: usize,
write_idx: usize,
}
#[derive(Debug)]
struct Full;
impl<T: Clone> RingBuffer<T> {
fn new(capacity: usize) -> Self {
RingBuffer {
storage: vec![None; capacity],
read_idx: 1,
write_idx: 0,
}
}
fn push(&mut self, item: T) -> Result<(), Full> {
if self.is_full() {
return Err(Full);
}
self.storage[self.write_idx] = Some(item);
self.write_idx = self.advance_idx(self.write_idx);
Ok(())
}
fn pull(&self) -> Option<T> {
if self.is_empty() {
return None;
}
if let Some(item) = &self.storage[self.write_idx] {
Some(item.clone())
} else {
None
}
}
fn advance_idx(&self, idx: usize) -> usize {
(idx + 1) % self.storage.len()
}
fn is_empty(&self) -> bool {
todo!()
}
fn is_full(&self) -> bool {
((self.write_idx as i64) - (self.read_idx as i64)) + 1 == self.storage.len() as i64
}
}
fn main() {
println!("Hello, Internet! Let's learn about ring buffers!");
let mut b = RingBuffer::<i32>::new(100);
let _ = b.pull();
let _ = b.push(10);
// let _ = b.push(20);
// println!("{r1:?}");
println!("{:?}", b.is_empty());
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment