Skip to content

Instantly share code, notes, and snippets.

@saethlin
Created May 24, 2017 22:33
Show Gist options
  • Save saethlin/c0d366b0c6023c6bdf0db97c42b34a40 to your computer and use it in GitHub Desktop.
Save saethlin/c0d366b0c6023c6bdf0db97c42b34a40 to your computer and use it in GitHub Desktop.
A fixed-size circular buffer for use in implementing shell history
struct CircularBuffer<T> {
buffer: Vec<T>,
head: usize,
tail: usize,
}
impl <T: Default> CircularBuffer<T>{
pub fn new(size: usize) -> Self {
CircularBuffer {
buffer: vec![Default::default(); size],
head: 0,
tail: 0,
}
}
pub fn push(&mut self, entry: T) {
self.tail += 1;
if self.tail > self.buffer.len() {
self.tail = 0;
}
self.buffer[self.tail] = entry;
if self.head == self.tail {
self.head += 1;
if self.head > self.history.size {
self.head = 0;
}
}
}
pub fn iter(&self) {
CircularBufferIter {
buffer: self,
position: self.head,
}
}
pub fn tail(&self) -> Option<T> {
if self.head == self.tail {
None
}
else {
Some(self.buffer[self.tail])
}
}
}
struct CircularBufferIter<'a, T> {
position: usize,
buffer: &'a CircularBuffer<T>,
}
impl <'a, T: Default>Iterator for CircularBufferIter<'a, T> {
type Item = T;
fn next(&mut self) -> Option<&T> {
if self.position == self.buffer.tail {
None
}
else {
self.position += 1;
if self.position > self.buffer.buffer.len() {
self.position = 0;
}
Some(self.buffer.buffer[self.position])
}
}
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment