1use std::hash::Hasher;
7
8use derive_more::Deref;
9
10pub type HashId = u64;
12
13pub use rustc_hash::FxHashMap as HashMap;
14pub use rustc_hash::FxHashSet as HashSet;
15
16pub trait ComputedHash {
18 fn computed_hash(&self) -> HashId;
20}
21
22#[derive(Deref, Debug, Clone)]
24pub struct Hashed<T: std::hash::Hash> {
25 #[deref]
26 inner: T,
27 hash: HashId,
28}
29
30impl<T: std::hash::Hash> Hashed<T> {
31 pub fn new(inner: T) -> Self {
33 let mut hasher = rustc_hash::FxHasher::default();
34 inner.hash(&mut hasher);
35 Self {
36 inner,
37 hash: hasher.finish(),
38 }
39 }
40
41 pub fn map<U: std::hash::Hash, F>(self, f: F) -> Hashed<U>
43 where
44 F: FnOnce(T) -> U,
45 {
46 let new_inner = f(self.inner);
48
49 Hashed::new(new_inner)
51 }
52
53 pub fn value(&self) -> &T {
55 &self.inner
56 }
57}
58
59impl<T: std::hash::Hash> ComputedHash for Hashed<T> {
60 fn computed_hash(&self) -> HashId {
61 self.hash
62 }
63}