use std::borrow::{Borrow, ToOwned}; use std::hash::Hash; use std::sync::Arc; use crate::dict::Dict; use crate::set::Set; use crate::shared::Shared; use crate::traits::Immutable; use crate::{ArcArray, Str}; #[derive(Debug)] pub struct CacheSet(Shared>>); impl Default for CacheSet { fn default() -> Self { Self::new() } } impl CacheSet { pub fn new() -> Self { Self(Shared::new(Set::new())) } } impl Clone for CacheSet { fn clone(&self) -> Self { Self(self.0.clone()) } } impl Clone for CacheSet { fn clone(&self) -> Self { Self(self.0.clone()) } } impl CacheSet { pub fn get(&self, s: &str) -> Str { if let Some(cached) = self.0.borrow().get(s) { return cached.clone().into(); } // &self.0 is dropped let s = Str::rc(s); self.0.borrow_mut().insert(s.clone().into_rc()); s } } impl CacheSet<[T]> { pub fn get(&self, q: &[T]) -> Arc<[T]> { if let Some(cached) = self.0.borrow().get(q) { return cached.clone(); } // &self.0 is dropped let s = ArcArray::from(q); self.0.borrow_mut().insert(s.clone()); s } } impl CacheSet<[T]> { pub fn linear_get(&self, q: &[T]) -> Arc<[T]> { if let Some(cached) = self.0.borrow().linear_get(q) { return cached.clone(); } // &self.0 is dropped let s = ArcArray::from(q); self.0.borrow_mut().insert(s.clone()); s } } impl CacheSet { pub fn get(&self, q: &Q) -> Arc where Arc: Borrow, Q: ?Sized + Hash + Eq + ToOwned, { if let Some(cached) = self.0.borrow().get(q) { return cached.clone(); } // &self.0 is dropped let s = Arc::from(q.to_owned()); self.0.borrow_mut().insert(s.clone()); s } } impl CacheSet { pub fn linear_get(&self, q: &Q) -> Arc where Arc: Borrow, Q: ?Sized + Eq + ToOwned, { if let Some(cached) = self.0.borrow().linear_get(q) { return cached.clone(); } // &self.0 is dropped let s = Arc::from(q.to_owned()); self.0.borrow_mut().insert(s.clone()); s } } #[derive(Debug, Clone)] pub struct CacheDict(Shared>>); impl Default for CacheDict { fn default() -> Self { Self::new() } } impl CacheDict { pub fn new() -> Self { Self(Shared::new(Dict::new())) } } impl CacheDict { pub fn get(&self, k: &Q) -> Option> where K: Borrow, { self.0.borrow().get(k).cloned() } } impl CacheDict { pub fn insert(&self, k: K, v: V) { self.0.borrow_mut().insert(k, Arc::new(v)); } } impl CacheDict { pub fn linear_get(&self, k: &Q) -> Option> where K: Borrow, { self.0.borrow().linear_get(k).cloned() } }