1 use std::collections::VecDeque;
2 use std::ops::{Index, IndexMut};
4 /// A view onto a finite range of an infinitely long sequence of T.
6 /// The Ts are indexed 0..infinity. A RingBuffer begins as a view of elements
7 /// 0..0 (i.e. nothing). The user of the RingBuffer advances its left and right
8 /// position independently, although only in the positive direction, and only
9 /// with left <= right at all times.
11 /// Holding a RingBuffer whose view is elements left..right gives the ability to
12 /// use Index and IndexMut to access elements i in the infinitely long queue for
13 /// which left <= i < right.
14 pub struct RingBuffer<T> {
16 // Abstract index of data[0] in the infinitely sized queue.
20 impl<T> RingBuffer<T> {
21 pub fn new() -> Self {
22 RingBuffer { data: VecDeque::new(), offset: 0 }
25 pub fn is_empty(&self) -> bool {
29 pub fn push(&mut self, value: T) -> usize {
30 let index = self.offset + self.data.len();
31 self.data.push_back(value);
35 pub fn clear(&mut self) {
39 pub fn index_of_first(&self) -> usize {
43 pub fn first(&self) -> Option<&T> {
47 pub fn first_mut(&mut self) -> Option<&mut T> {
51 pub fn pop_first(&mut self) -> Option<T> {
52 let first = self.data.pop_front()?;
57 pub fn last(&self) -> Option<&T> {
61 pub fn last_mut(&mut self) -> Option<&mut T> {
66 impl<T> Index<usize> for RingBuffer<T> {
68 fn index(&self, index: usize) -> &Self::Output {
69 &self.data[index.checked_sub(self.offset).unwrap()]
73 impl<T> IndexMut<usize> for RingBuffer<T> {
74 fn index_mut(&mut self, index: usize) -> &mut Self::Output {
75 &mut self.data[index.checked_sub(self.offset).unwrap()]