pub struct PushBuffer<T> {
data: Vec<T>,
}
impl<T> PushBuffer<T> {
pub fn new(capacity: usize) -> Self {
assert!(capacity > 0);
Self {
data: Vec::with_capacity(capacity),
}
}
pub fn len(&self) -> usize {
self.data.len()
}
pub fn is_empty(&self) -> bool {
self.data.len() == 0
}
pub fn capacity(&self) -> usize {
self.data.capacity()
}
pub fn start_pass(&mut self) -> PushBufferPass<'_, T> {
self.data.clear();
PushBufferPass::new(self)
}
pub fn data(&self) -> &[T] {
&self.data
}
}
pub struct PushBufferPass<'a, T> {
push_buffer: &'a mut PushBuffer<T>,
}
impl<'a, T> PushBufferPass<'a, T> {
pub fn new(push_buffer: &'a mut PushBuffer<T>) -> Self {
Self { push_buffer }
}
pub fn push(&mut self, element: T) {
self.push_buffer.data.push(element);
}
}
#[cfg(test)]
mod tests {
use super::*;
#[test]
fn push_buffer_grows() {
let mut push_buffer = PushBuffer::<u32>::new(4);
assert_eq!(push_buffer.len(), 0);
assert_eq!(push_buffer.capacity(), 4);
{
let mut pass = push_buffer.start_pass();
for i in 0..8 {
pass.push(i + 1);
}
}
assert_eq!(push_buffer.len(), 8);
assert_eq!(push_buffer.data(), &(1..9).collect::<Vec<_>>());
assert!(push_buffer.capacity() >= 8);
{
let _pass = push_buffer.start_pass();
}
assert_eq!(push_buffer.len(), 0);
}
}