use std::collections::VecDeque;
use std::time::Duration;
use super::core::WorkItem;
#[derive(Debug)]
pub struct WorkQueue<T: Clone> {
pub items: VecDeque<WorkItem<T>>,
pub processed_count: usize,
pub total_time: Duration,
pub avg_time: Duration,
}
impl<T: Clone> Default for WorkQueue<T> {
fn default() -> Self {
Self {
items: VecDeque::new(),
processed_count: 0,
total_time: Duration::ZERO,
avg_time: Duration::ZERO,
}
}
}
impl<T: Clone> WorkQueue<T> {
pub fn push_front(&mut self, item: WorkItem<T>) {
self.items.push_front(item);
}
#[allow(dead_code)]
pub fn push_back(&mut self, item: WorkItem<T>) {
self.items.push_back(item);
}
pub fn pop_front(&mut self) -> Option<WorkItem<T>> {
self.items.pop_front()
}
pub fn steal_back(&mut self) -> Option<WorkItem<T>> {
if self.items.len() > 1 {
self.items.pop_back()
} else {
None
}
}
pub fn update_timing(&mut self, executiontime: Duration) {
self.processed_count += 1;
self.total_time += executiontime;
self.avg_time = self.total_time / self.processed_count as u32;
}
pub fn estimated_load(&self) -> Duration {
let base_time = if self.avg_time.is_zero() {
Duration::from_millis(1) } else {
self.avg_time
};
self.items
.iter()
.map(|item| item.estimated_time.unwrap_or(base_time))
.sum()
}
}