use std::collections::{BTreeMap, BTreeSet, HashMap, HashSet};
use std::hash::{BuildHasher, Hash};
pub trait TryIndex<Idx: ?Sized> {
type Output;
fn try_index(&self, index: &Idx) -> Option<&Self::Output>;
fn try_remove(&mut self, index: &Idx) -> Option<Self::Output>;
}
pub trait TryIndexMut<Idx: ?Sized>: TryIndex<Idx> {
fn try_index_mut(&mut self, index: &Idx) -> Option<&mut Self::Output>;
}
impl<K, V, S> TryIndex<K> for HashMap<K, V, S>
where
K: Hash + Eq,
S: BuildHasher,
{
type Output = V;
fn try_index(&self, index: &K) -> Option<&V> {
self.get(index)
}
fn try_remove(&mut self, index: &K) -> Option<V> {
self.remove(index)
}
}
impl<K, V, S> TryIndexMut<K> for HashMap<K, V, S>
where
K: Hash + Eq,
S: BuildHasher,
{
fn try_index_mut(&mut self, index: &K) -> Option<&mut V> {
self.get_mut(index)
}
}
impl<K, V> TryIndex<K> for BTreeMap<K, V>
where
K: Ord,
{
type Output = V;
fn try_index(&self, index: &K) -> Option<&V> {
self.get(index)
}
fn try_remove(&mut self, index: &K) -> Option<V> {
self.remove(index)
}
}
impl<K, V> TryIndexMut<K> for BTreeMap<K, V>
where
K: Ord,
{
fn try_index_mut(&mut self, index: &K) -> Option<&mut V> {
self.get_mut(index)
}
}
impl<T, S> TryIndex<T> for HashSet<T, S>
where
T: Hash + Eq,
S: BuildHasher,
{
type Output = T;
fn try_index(&self, index: &T) -> Option<&T> {
self.get(index)
}
fn try_remove(&mut self, index: &T) -> Option<T> {
self.take(index)
}
}
impl<T> TryIndex<T> for BTreeSet<T>
where
T: Ord,
{
type Output = T;
fn try_index(&self, index: &T) -> Option<&T> {
self.get(index)
}
fn try_remove(&mut self, index: &T) -> Option<T> {
self.take(index)
}
}