feat: simple mempool added

This commit is contained in:
Oleksandr Pravdyvyi 2024-10-07 13:35:29 +03:00
parent 8de1d226f0
commit 08d5d6454d
2 changed files with 173 additions and 1 deletions

View File

@ -1 +1,169 @@
//ToDo: Add mempool module
use std::collections::VecDeque;
use mempoolitem::MemPoolItem;
pub mod mempoolitem;
pub struct MemPool<Item: MemPoolItem> {
items: VecDeque<Item>,
}
impl<Item: MemPoolItem> MemPool<Item> {
pub fn new() -> Self {
Self {
items: VecDeque::new(),
}
}
pub fn pop_last(&mut self) -> Option<Item> {
self.items.pop_front()
}
pub fn peek_last(&self) -> Option<&Item> {
self.items.front()
}
pub fn push_item(&mut self, item: Item) {
self.items.push_back(item);
}
pub fn len(&self) -> usize {
self.items.len()
}
pub fn is_empty(&self) -> bool {
self.len() == 0
}
pub fn pop_size(&mut self, size: usize) -> Vec<Item> {
let mut ret_vec = vec![];
for _ in 0..size {
let item = self.pop_last();
match item {
Some(item) => ret_vec.push(item),
None => break,
}
}
ret_vec
}
pub fn drain_size(&mut self, remainder: usize) -> Vec<Item> {
self.pop_size(self.len().saturating_sub(remainder))
}
}
impl<Item: MemPoolItem> Default for MemPool<Item> {
fn default() -> Self {
Self::new()
}
}
#[cfg(test)]
mod tests {
use std::vec;
use super::*;
pub type ItemId = u64;
#[derive(Debug, PartialEq, Eq)]
pub struct TestItem {
id: ItemId,
}
impl MemPoolItem for TestItem {
type Identifier = ItemId;
fn identifier(&self) -> Self::Identifier {
self.id
}
}
fn test_item_with_id(id: u64) -> TestItem {
TestItem { id }
}
#[test]
fn test_create_empty_mempool() {
let _: MemPool<TestItem> = MemPool::new();
}
#[test]
fn test_push_pop() {
let mut mempool: MemPool<TestItem> = MemPool::new();
let items = vec![
test_item_with_id(1),
test_item_with_id(2),
test_item_with_id(3),
];
for item in items {
mempool.push_item(item);
}
assert_eq!(mempool.len(), 3);
let item = mempool.pop_last();
assert_eq!(item, Some(TestItem { id: 1 }));
assert_eq!(mempool.len(), 2);
let item = mempool.pop_last();
assert_eq!(item, Some(TestItem { id: 2 }));
assert_eq!(mempool.len(), 1);
let item = mempool.pop_last();
assert_eq!(item, Some(TestItem { id: 3 }));
assert_eq!(mempool.len(), 0);
let item = mempool.pop_last();
assert_eq!(item, None);
}
#[test]
fn test_pop_many() {
let mut mempool: MemPool<TestItem> = MemPool::new();
let mut items = vec![];
for i in 1..11 {
items.push(test_item_with_id(i));
}
for item in items {
mempool.push_item(item);
}
assert_eq!(mempool.len(), 10);
let items1 = mempool.pop_size(4);
assert_eq!(
items1,
vec![
test_item_with_id(1),
test_item_with_id(2),
test_item_with_id(3),
test_item_with_id(4)
]
);
assert_eq!(mempool.len(), 6);
let items2 = mempool.drain_size(2);
assert_eq!(
items2,
vec![
test_item_with_id(5),
test_item_with_id(6),
test_item_with_id(7),
test_item_with_id(8)
]
);
assert_eq!(mempool.len(), 2);
}
}

View File

@ -0,0 +1,4 @@
pub trait MemPoolItem {
type Identifier;
fn identifier(&self) -> Self::Identifier;
}