mirror of
https://github.com/rust-lang/rust.git
synced 2025-05-08 07:57:40 +00:00
62 lines
1.7 KiB
Rust
62 lines
1.7 KiB
Rust
use crate::fx::FxHashMap;
|
|
use arrayvec::ArrayVec;
|
|
|
|
use std::hash::Hash;
|
|
|
|
/// Small-storage-optimized implementation of a map
|
|
/// made specifically for caching results.
|
|
///
|
|
/// Stores elements in a small array up to a certain length
|
|
/// and switches to `HashMap` when that length is exceeded.
|
|
pub enum MiniMap<K, V> {
|
|
Array(ArrayVec<[(K, V); 8]>),
|
|
Map(FxHashMap<K, V>),
|
|
}
|
|
|
|
impl<K: Eq + Hash, V> MiniMap<K, V> {
|
|
/// Creates an empty `MiniMap`.
|
|
pub fn new() -> Self {
|
|
MiniMap::Array(ArrayVec::new())
|
|
}
|
|
|
|
/// Inserts or updates value in the map.
|
|
pub fn insert(&mut self, key: K, value: V) {
|
|
match self {
|
|
MiniMap::Array(array) => {
|
|
for pair in array.iter_mut() {
|
|
if pair.0 == key {
|
|
pair.1 = value;
|
|
return;
|
|
}
|
|
}
|
|
if let Err(error) = array.try_push((key, value)) {
|
|
let mut map: FxHashMap<K, V> = array.drain(..).collect();
|
|
let (key, value) = error.element();
|
|
map.insert(key, value);
|
|
*self = MiniMap::Map(map);
|
|
}
|
|
}
|
|
MiniMap::Map(map) => {
|
|
map.insert(key, value);
|
|
}
|
|
}
|
|
}
|
|
|
|
/// Return value by key if any.
|
|
pub fn get(&self, key: &K) -> Option<&V> {
|
|
match self {
|
|
MiniMap::Array(array) => {
|
|
for pair in array {
|
|
if pair.0 == *key {
|
|
return Some(&pair.1);
|
|
}
|
|
}
|
|
return None;
|
|
}
|
|
MiniMap::Map(map) => {
|
|
return map.get(key);
|
|
}
|
|
}
|
|
}
|
|
}
|