1use std::pin::Pin;
2
3use object_rainbow::{
4 Enum, Fetch, Hash, Inline, InlineOutput, ListHashes, MaybeHasNiche, Output, Parse, ParseInline,
5 PointInput, PointVisitor, Size, Tagged, Tags, ToOutput, Topological, Traversible, assert_impl,
6};
7use object_rainbow_array_map::ArrayMap;
8use object_rainbow_point::{IntoPoint, Point};
9
10type OptionFuture<'a, T> =
11 Pin<Box<dyn 'a + Send + Future<Output = object_rainbow::Result<Option<T>>>>>;
12
13trait Amt<K> {
14 type V: Send + Sync;
15 fn insert(&mut self, key: K, value: Self::V) -> OptionFuture<'_, Self::V>;
16 fn from_pair(a: (K, Self::V), b: (K, Self::V)) -> Self;
17 fn get(&self, key: K) -> OptionFuture<'_, Self::V>;
18}
19
20#[derive(ToOutput, Tagged, ListHashes, Topological, Parse, Clone)]
21struct DeepestLeaf<V = ()>(ArrayMap<V>);
23
24impl<V: Send + Sync + Clone> Amt<u8> for DeepestLeaf<V> {
25 type V = V;
26
27 fn insert(&mut self, key: u8, value: Self::V) -> OptionFuture<'_, Self::V> {
28 Box::pin(async move { Ok(self.0.insert(key, value)) })
29 }
30
31 fn from_pair(a: (u8, Self::V), b: (u8, Self::V)) -> Self {
32 Self([a, b].into())
33 }
34
35 fn get(&self, key: u8) -> OptionFuture<'_, Self::V> {
36 Box::pin(async move { Ok(self.0.get(key).cloned()) })
37 }
38}
39
40#[derive(Enum, ToOutput, InlineOutput, Tagged, ListHashes, Topological, Parse, ParseInline)]
41enum SubTree<T, K, V = <T as Amt<K>>::V> {
42 Leaf(K, V),
43 SubTree(Point<T>),
44}
45
46impl<T, K: Clone, V: Clone> Clone for SubTree<T, K, V> {
47 fn clone(&self) -> Self {
48 match self {
49 Self::Leaf(key, value) => Self::Leaf(key.clone(), value.clone()),
50 Self::SubTree(point) => Self::SubTree(point.clone()),
51 }
52 }
53}
54
55impl<T: Amt<K, V: Clone> + Clone + Traversible, K: Send + Sync + PartialEq + Clone> Amt<K>
56 for SubTree<T, K>
57{
58 type V = T::V;
59
60 fn insert(&mut self, key: K, value: Self::V) -> OptionFuture<'_, Self::V> {
61 Box::pin(async move {
62 match self {
63 SubTree::Leaf(xkey, xvalue) => Ok(if *xkey != key {
64 *self = Self::from_pair((xkey.clone(), xvalue.clone()), (key, value));
65 None
66 } else {
67 Some(std::mem::replace(xvalue, value))
68 }),
69 SubTree::SubTree(sub) => sub.fetch_mut().await?.insert(key, value).await,
70 }
71 })
72 }
73
74 fn from_pair(a: (K, Self::V), b: (K, Self::V)) -> Self {
75 Self::SubTree(T::from_pair(a, b).point())
76 }
77
78 fn get(&self, key: K) -> OptionFuture<'_, Self::V> {
79 Box::pin(async move {
80 match self {
81 SubTree::Leaf(existing, value) => Ok((*existing == key).then(|| value.clone())),
82 SubTree::SubTree(sub) => sub.fetch().await?.get(key).await,
83 }
84 })
85 }
86}
87
88#[derive(ToOutput, Tagged, ListHashes, Topological, Parse)]
89struct SetNode<T, K, V = <T as Amt<K>>::V>(ArrayMap<SubTree<T, K, V>>);
90
91impl<T, K: Clone, V: Clone> Clone for SetNode<T, K, V> {
92 fn clone(&self) -> Self {
93 Self(self.0.clone())
94 }
95}
96
97impl<T, K, V> Default for SetNode<T, K, V> {
98 fn default() -> Self {
99 Self(Default::default())
100 }
101}
102
103impl<T: Amt<K, V: Clone> + Clone + Traversible, K: Send + Sync + PartialEq + Clone> Amt<(u8, K)>
104 for SetNode<T, K>
105{
106 type V = T::V;
107
108 fn insert(&mut self, (key, rest): (u8, K), value: Self::V) -> OptionFuture<'_, Self::V> {
109 Box::pin(async move {
110 if let Some(sub) = self.0.get_mut(key) {
111 sub.insert(rest, value).await
112 } else {
113 assert!(self.0.insert(key, SubTree::Leaf(rest, value)).is_none());
114 Ok(None)
115 }
116 })
117 }
118
119 fn from_pair(
120 ((a, rest_a), value_a): ((u8, K), Self::V),
121 ((b, rest_b), value_b): ((u8, K), Self::V),
122 ) -> Self {
123 if a == b {
124 Self([(a, SubTree::from_pair((rest_a, value_a), (rest_b, value_b)))].into())
125 } else {
126 Self(
127 [
128 (a, SubTree::Leaf(rest_a, value_a)),
129 (b, SubTree::Leaf(rest_b, value_b)),
130 ]
131 .into(),
132 )
133 }
134 }
135
136 fn get(&self, (key, rest): (u8, K)) -> OptionFuture<'_, Self::V> {
137 Box::pin(async move {
138 if let Some(sub) = self.0.get(key) {
139 sub.get(rest).await
140 } else {
141 Ok(None)
142 }
143 })
144 }
145}
146
147type K1 = u8;
148type K2 = (u8, K1);
149type K3 = (u8, K2);
150type K4 = (u8, K3);
151type K5 = (u8, K4);
152type K6 = (u8, K5);
153type K7 = (u8, K6);
154type K8 = (u8, K7);
155type K9 = (u8, K8);
156type K10 = (u8, K9);
157type K11 = (u8, K10);
158type K12 = (u8, K11);
159type K13 = (u8, K12);
160type K14 = (u8, K13);
161type K15 = (u8, K14);
162type K16 = (u8, K15);
163type K17 = (u8, K16);
164type K18 = (u8, K17);
165type K19 = (u8, K18);
166type K20 = (u8, K19);
167type K21 = (u8, K20);
168type K22 = (u8, K21);
169type K23 = (u8, K22);
170type K24 = (u8, K23);
171type K25 = (u8, K24);
172type K26 = (u8, K25);
173type K27 = (u8, K26);
174type K28 = (u8, K27);
175type K29 = (u8, K28);
176type K30 = (u8, K29);
177type K31 = (u8, K30);
178type K32 = (u8, K31);
179
180mod private {
181 use super::*;
182 type N1<V = ()> = DeepestLeaf<V>;
183
184 macro_rules! next_node {
185 ($prev:ident, $next:ident, $pk:ident, $k:ident) => {
186 #[derive(Clone)]
187 pub struct $next<V = ()>(SetNode<$prev<V>, $pk, V>);
188
189 impl<V> Default for $next<V> {
190 fn default() -> Self {
191 Self(Default::default())
192 }
193 }
194
195 impl<V: ParseInline<I> + Inline<I::Extra>, I: PointInput<Extra: Send + Sync>> Parse<I>
196 for $next<V>
197 {
198 fn parse(input: I) -> object_rainbow::Result<Self> {
199 Ok(Self(input.parse()?))
200 }
201 }
202
203 impl<V: Tagged> Tagged for $next<V> {
204 const TAGS: Tags = V::TAGS;
205 }
206
207 impl<V: InlineOutput> ToOutput for $next<V> {
208 fn to_output(&self, output: &mut dyn Output) {
209 self.0.to_output(output);
210 }
211 }
212
213 impl<V: ListHashes> ListHashes for $next<V> {
214 fn list_hashes(&self, f: &mut impl FnMut(Hash)) {
215 self.0.list_hashes(f)
216 }
217 }
218
219 impl<V: Traversible + InlineOutput> Topological for $next<V> {
220 fn traverse(&self, visitor: &mut impl PointVisitor) {
221 self.0.traverse(visitor)
222 }
223 }
224
225 impl<V: Traversible + InlineOutput + Clone> Amt<$k> for $next<V> {
226 type V = V;
227
228 fn insert(&mut self, key: $k, value: Self::V) -> OptionFuture<'_, Self::V> {
229 self.0.insert(key, value)
230 }
231
232 fn from_pair(a: ($k, Self::V), b: ($k, Self::V)) -> Self {
233 Self(Amt::from_pair(a, b))
234 }
235
236 fn get(&self, key: $k) -> OptionFuture<'_, Self::V> {
237 self.0.get(key)
238 }
239 }
240 };
241 }
242
243 next_node!(N1, N2, K1, K2);
244 next_node!(N2, N3, K2, K3);
245 next_node!(N3, N4, K3, K4);
246 next_node!(N4, N5, K4, K5);
247 next_node!(N5, N6, K5, K6);
248 next_node!(N6, N7, K6, K7);
249 next_node!(N7, N8, K7, K8);
250 next_node!(N8, N9, K8, K9);
251 next_node!(N9, N10, K9, K10);
252 next_node!(N10, N11, K10, K11);
253 next_node!(N11, N12, K11, K12);
254 next_node!(N12, N13, K12, K13);
255 next_node!(N13, N14, K13, K14);
256 next_node!(N14, N15, K14, K15);
257 next_node!(N15, N16, K15, K16);
258 next_node!(N16, N17, K16, K17);
259 next_node!(N17, N18, K17, K18);
260 next_node!(N18, N19, K18, K19);
261 next_node!(N19, N20, K19, K20);
262 next_node!(N20, N21, K20, K21);
263 next_node!(N21, N22, K21, K22);
264 next_node!(N22, N23, K22, K23);
265 next_node!(N23, N24, K23, K24);
266 next_node!(N24, N25, K24, K25);
267 next_node!(N25, N26, K25, K26);
268 next_node!(N26, N27, K26, K27);
269 next_node!(N27, N28, K27, K28);
270 next_node!(N28, N29, K28, K29);
271 next_node!(N29, N30, K29, K30);
272 next_node!(N30, N31, K30, K31);
273 next_node!(N31, N32, K31, K32);
274}
275
276#[derive(
277 ToOutput, InlineOutput, Tagged, ListHashes, Topological, Parse, ParseInline, Size, MaybeHasNiche,
278)]
279pub struct HamtMap<V>(Point<private::N32<V>>);
280
281assert_impl!(
282 impl<V, E> Inline<E> for HamtMap<V>
283 where
284 E: 'static + Send + Sync + Clone,
285 V: Inline<E>,
286 {
287 }
288);
289
290impl<V> Clone for HamtMap<V> {
291 fn clone(&self) -> Self {
292 Self(self.0.clone())
293 }
294}
295
296impl<V> PartialEq for HamtMap<V> {
297 fn eq(&self, other: &Self) -> bool {
298 self.0 == other.0
299 }
300}
301
302impl<V> Eq for HamtMap<V> {}
303
304impl<V: Traversible + InlineOutput + Clone> Default for HamtMap<V> {
305 fn default() -> Self {
306 Self(Default::default())
307 }
308}
309
310impl<V: Traversible + InlineOutput + Clone> HamtMap<V> {
311 pub fn new() -> Self {
312 Self::default()
313 }
314
315 pub async fn insert(&mut self, hash: Hash, value: V) -> object_rainbow::Result<Option<V>> {
316 self.0
317 .fetch_mut()
318 .await?
319 .insert(hash_key(hash), value)
320 .await
321 }
322
323 pub async fn get(&self, hash: Hash) -> object_rainbow::Result<Option<V>> {
324 self.0.fetch().await?.get(hash_key(hash)).await
325 }
326}
327
328fn hash_key(hash: Hash) -> K32 {
329 let [
330 x0,
331 x1,
332 x2,
333 x3,
334 x4,
335 x5,
336 x6,
337 x7,
338 x8,
339 x9,
340 x10,
341 x11,
342 x12,
343 x13,
344 x14,
345 x15,
346 x16,
347 x17,
348 x18,
349 x19,
350 x20,
351 x21,
352 x22,
353 x23,
354 x24,
355 x25,
356 x26,
357 x27,
358 x28,
359 x29,
360 x30,
361 x31,
362 ] = hash.into_bytes();
363 (x0,(x1,(x2,(x3,(x4,(x5,(x6,(x7,(x8,(x9,(x10,(x11,(x12,(x13,(x14,(x15,(x16,(x17,(x18,(x19,(x20,(x21,(x22,(x23,(x24,(x25,(x26,(x27,(x28,(x29,(x30,(x31))))))))))))))))))))))))))))))))
364}
365
366#[derive(
367 ToOutput,
368 InlineOutput,
369 Tagged,
370 ListHashes,
371 Topological,
372 Parse,
373 ParseInline,
374 Size,
375 MaybeHasNiche,
376 Clone,
377 Default,
378 PartialEq,
379 Eq,
380)]
381pub struct HamtSet(HamtMap<()>);
382
383assert_impl!(
384 impl<E> Inline<E> for HamtSet where E: 'static + Send + Sync + Clone {}
385);
386
387impl HamtSet {
388 pub fn new() -> Self {
389 Self::default()
390 }
391
392 pub async fn insert(&mut self, hash: Hash) -> object_rainbow::Result<bool> {
393 Ok(self.0.insert(hash, ()).await?.is_none())
394 }
395
396 pub async fn contains(&self, hash: Hash) -> object_rainbow::Result<bool> {
397 Ok(self.0.get(hash).await?.is_some())
398 }
399}