1use std::borrow::Borrow;
2use std::collections::BTreeMap;
3use std::marker::PhantomData;
4
5use super::raw::*;
6use super::typed::*;
7use super::{
8 DictKey, LoadDictKey, SearchByExtra, SetMode, StoreDictKey, aug_dict_find_by_extra,
9 aug_dict_insert, aug_dict_merge_siblings, aug_dict_modify_from_sorted_iter,
10 aug_dict_remove_owned, build_aug_dict_from_sorted_iter, read_label,
11};
12use crate::cell::*;
13use crate::error::*;
14use crate::util::*;
15
16pub trait AugDictExtra: Default {
18 fn comp_add(
26 left: &mut CellSlice,
27 right: &mut CellSlice,
28 b: &mut CellBuilder,
29 cx: &dyn CellContext,
30 ) -> Result<(), Error>;
31}
32
33pub struct AugDict<K, A, V> {
50 dict: Dict<K, (A, V)>,
51 extra: A,
52 _key: PhantomData<K>,
53 _value: PhantomData<(A, V)>,
54}
55
56impl<K, A: ExactSize, V> ExactSize for AugDict<K, A, V> {
57 #[inline]
58 fn exact_size(&self) -> Size {
59 self.dict.exact_size() + self.extra.exact_size()
60 }
61}
62
63impl<'a, K, A: Load<'a>, V> Load<'a> for AugDict<K, A, V> {
64 #[inline]
65 fn load_from(slice: &mut CellSlice<'a>) -> Result<Self, Error> {
66 Ok(Self {
67 dict: ok!(Dict::load_from(slice)),
68 extra: ok!(A::load_from(slice)),
69 _key: PhantomData,
70 _value: PhantomData,
71 })
72 }
73}
74
75impl<K, A: Store, V> Store for AugDict<K, A, V> {
76 #[inline]
77 fn store_into(
78 &self,
79 builder: &mut CellBuilder,
80 context: &dyn CellContext,
81 ) -> Result<(), Error> {
82 ok!(self.dict.store_into(builder, context));
83 self.extra.store_into(builder, context)
84 }
85}
86
87impl<K, A: Default, V> Default for AugDict<K, A, V> {
88 #[inline]
89 fn default() -> Self {
90 Self::new()
91 }
92}
93
94impl<K, A: Clone, V> Clone for AugDict<K, A, V> {
95 fn clone(&self) -> Self {
96 Self {
97 dict: self.dict.clone(),
98 extra: self.extra.clone(),
99 _key: PhantomData,
100 _value: PhantomData,
101 }
102 }
103}
104
105impl<K, A: Eq, V> Eq for AugDict<K, A, V> {}
106
107impl<K, A: PartialEq, V> PartialEq for AugDict<K, A, V> {
108 fn eq(&self, other: &Self) -> bool {
109 self.dict.eq(&other.dict) && self.extra.eq(&other.extra)
110 }
111}
112
113impl<K, A: std::fmt::Debug, V> std::fmt::Debug for AugDict<K, A, V> {
114 fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
115 debug_struct_field2_finish(f, "AugDict", "dict", &self.dict, "extra", &self.extra)
116 }
117}
118
119impl<K, A: Default, V> AugDict<K, A, V> {
120 pub fn new() -> Self {
122 Self {
123 dict: Dict::new(),
124 extra: A::default(),
125 _key: PhantomData,
126 _value: PhantomData,
127 }
128 }
129
130 pub const fn from_parts(dict: Dict<K, (A, V)>, extra: A) -> Self {
132 Self {
133 dict,
134 extra,
135 _key: PhantomData,
136 _value: PhantomData,
137 }
138 }
139
140 pub fn into_parts(self) -> (Dict<K, (A, V)>, A) {
142 (self.dict, self.extra)
143 }
144
145 #[inline]
147 pub fn cast_into<Q, T>(self) -> AugDict<Q, A, T>
148 where
149 Q: EquivalentRepr<K>,
150 (A, T): EquivalentRepr<(A, V)>,
151 {
152 AugDict {
153 dict: self.dict.cast_into(),
154 extra: self.extra,
155 _key: PhantomData,
156 _value: PhantomData,
157 }
158 }
159}
160
161impl<K: DictKey, A, V> AugDict<K, A, V> {
162 pub fn load_from_root_ext<'a>(
164 slice: &mut CellSlice<'a>,
165 context: &dyn CellContext,
166 ) -> Result<Self, Error>
167 where
168 A: Load<'a>,
169 V: Load<'a>,
170 {
171 let (extra, root) = ok!(load_from_root::<A, V>(slice, K::BITS, context));
172
173 Ok(Self {
174 dict: Dict::from(Some(root)),
175 extra,
176 _key: PhantomData,
177 _value: PhantomData,
178 })
179 }
180}
181
182impl<K, A, V> AugDict<K, A, V>
183where
184 K: DictKey,
185 for<'a> A: Default + Load<'a>,
186{
187 pub fn update_root_extra(&mut self) -> Result<(), Error> {
189 self.extra = match &self.dict.root {
190 Some(root) => {
191 let slice = &mut ok!(root.as_slice());
192 let prefix = ok!(read_label(slice, K::BITS));
193 if prefix.size_bits() != K::BITS {
194 ok!(slice.skip_first(0, 2));
195 }
196 ok!(A::load_from(slice))
197 }
198 None => A::default(),
199 };
200 Ok(())
201 }
202}
203
204fn load_from_root<'a, A, V>(
205 slice: &mut CellSlice<'a>,
206 key_bit_len: u16,
207 context: &dyn CellContext,
208) -> Result<(A, Cell), Error>
209where
210 A: Load<'a>,
211 V: Load<'a>,
212{
213 let root = *slice;
214
215 let label = ok!(read_label(slice, key_bit_len));
216 let extra = if label.size_bits() != key_bit_len {
217 ok!(slice.skip_first(0, 2));
218 ok!(A::load_from(slice))
219 } else {
220 let extra = ok!(A::load_from(slice));
221 ok!(V::load_from(slice));
222 extra
223 };
224
225 let root_bits = root.size_bits() - slice.size_bits();
226 let root_refs = root.size_refs() - slice.size_refs();
227
228 let mut b = CellBuilder::new();
229 ok!(b.store_slice(root.get_prefix(root_bits, root_refs)));
230 match b.build_ext(context) {
231 Ok(cell) => Ok((extra, cell)),
232 Err(e) => Err(e),
233 }
234}
235
236impl<K, A, V> AugDict<K, A, V> {
237 pub const fn is_empty(&self) -> bool {
239 self.dict.is_empty()
240 }
241
242 #[inline]
244 pub const fn dict(&self) -> &Dict<K, (A, V)> {
245 &self.dict
246 }
247
248 #[inline]
250 pub const fn root_extra(&self) -> &A {
251 &self.extra
252 }
253}
254
255impl<K, A, V> AugDict<K, A, V>
256where
257 K: StoreDictKey,
258{
259 pub fn contains_key<Q>(&self, key: Q) -> Result<bool, Error>
261 where
262 Q: Borrow<K>,
263 {
264 self.dict.contains_key(key)
265 }
266}
267
268impl<K, A, V> AugDict<K, A, V>
269where
270 K: StoreDictKey,
271{
272 pub fn get<'a: 'b, 'b, Q>(&'a self, key: Q) -> Result<Option<(A, V)>, Error>
274 where
275 Q: Borrow<K> + 'b,
276 (A, V): Load<'a>,
277 {
278 self.dict.get(key)
279 }
280}
281
282impl<K, A, V> AugDict<K, A, V>
283where
284 K: LoadDictKey,
285{
286 pub fn find_by_extra<'a, S>(&'a self, flow: S) -> Result<Option<(K, A, V)>, Error>
290 where
291 S: SearchByExtra<A>,
292 A: Load<'a>,
293 V: Load<'a>,
294 {
295 let Some((key, extra, mut value)) = ok!(aug_dict_find_by_extra::<A, S>(
296 self.dict.root.as_ref(),
297 K::BITS,
298 flow
299 )) else {
300 return Ok(None);
301 };
302
303 let Some(key) = K::load_from_data(&key) else {
304 return Err(Error::CellUnderflow);
305 };
306 let value = ok!(V::load_from(&mut value));
307 Ok(Some((key, extra, value)))
308 }
309}
310
311impl<K, A, V> AugDict<K, A, V>
312where
313 K: StoreDictKey,
314 for<'a> A: AugDictExtra + Store + Load<'a>,
315 V: Store,
316{
317 pub fn try_from_btree<Q, E, T>(sorted: &BTreeMap<Q, (E, T)>) -> Result<Self, Error>
319 where
320 Q: Borrow<K>,
321 E: Borrow<A>,
322 T: Borrow<V>,
323 K: DictKey + Ord,
324 {
325 let root = ok!(build_aug_dict_from_sorted_iter(
326 sorted
327 .iter()
328 .map(|(k, (a, v))| (k.borrow(), a.borrow(), v.borrow())),
329 A::comp_add,
330 Cell::empty_context()
331 ));
332
333 let mut result = Self {
334 dict: Dict::from_raw(root),
335 extra: A::default(),
336 _key: PhantomData,
337 _value: PhantomData,
338 };
339 ok!(result.update_root_extra());
340 Ok(result)
341 }
342
343 pub fn try_from_sorted_slice<Q, E, T>(sorted: &[(Q, E, T)]) -> Result<Self, Error>
345 where
346 Q: Borrow<K>,
347 E: Borrow<A>,
348 T: Borrow<V>,
349 K: Ord,
350 {
351 let root = ok!(build_aug_dict_from_sorted_iter(
352 sorted
353 .iter()
354 .map(|(k, a, v)| (k.borrow(), a.borrow(), v.borrow())),
355 A::comp_add,
356 Cell::empty_context()
357 ));
358
359 let mut result = Self {
360 dict: Dict::from_raw(root),
361 extra: A::default(),
362 _key: PhantomData,
363 _value: PhantomData,
364 };
365 ok!(result.update_root_extra());
366 Ok(result)
367 }
368
369 pub fn modify_with_sorted_iter<I>(&mut self, entries: I) -> Result<bool, Error>
374 where
375 I: IntoIterator<Item = (K, Option<(A, V)>)>,
376 K: Clone + Ord,
377 {
378 self.modify_with_sorted_iter_ext(
379 entries,
380 |(key, _)| key.clone(),
381 |(_, value)| Ok(value),
382 Cell::empty_context(),
383 )
384 }
385
386 pub fn modify_with_sorted_iter_ext<T, I, FK, FV>(
391 &mut self,
392 entries: I,
393 extract_key: FK,
394 extract_value: FV,
395 context: &dyn CellContext,
396 ) -> Result<bool, Error>
397 where
398 I: IntoIterator<Item = T>,
399 K: Ord,
400 for<'a> FK: FnMut(&'a T) -> K,
401 FV: FnMut(T) -> Result<Option<(A, V)>, Error>,
402 {
403 let modified = ok!(aug_dict_modify_from_sorted_iter(
404 &mut self.dict.root,
405 entries,
406 extract_key,
407 extract_value,
408 A::comp_add,
409 context,
410 ));
411
412 if modified {
413 ok!(self.update_root_extra());
414 }
415
416 Ok(modified)
417 }
418
419 pub fn set<Q, E, T>(&mut self, key: Q, aug: E, value: T) -> Result<bool, Error>
425 where
426 Q: Borrow<K>,
427 E: Borrow<A>,
428 T: Borrow<V>,
429 {
430 self.set_ext(key, aug, value, Cell::empty_context())
431 }
432
433 pub fn set_ext<Q, E, T>(
435 &mut self,
436 key: Q,
437 aug: E,
438 value: T,
439 context: &dyn CellContext,
440 ) -> Result<bool, Error>
441 where
442 Q: Borrow<K>,
443 E: Borrow<A>,
444 T: Borrow<V>,
445 {
446 self.insert_impl(
447 key.borrow(),
448 aug.borrow(),
449 value.borrow(),
450 SetMode::Set,
451 context,
452 )
453 }
454
455 pub fn replace<Q, E, T>(&mut self, key: Q, aug: E, value: T) -> Result<bool, Error>
462 where
463 Q: Borrow<K>,
464 E: Borrow<A>,
465 T: Borrow<V>,
466 {
467 self.replace_ext(key, aug, value, Cell::empty_context())
468 }
469
470 pub fn replace_ext<Q, E, T>(
473 &mut self,
474 key: Q,
475 aug: E,
476 value: T,
477 context: &dyn CellContext,
478 ) -> Result<bool, Error>
479 where
480 Q: Borrow<K>,
481 E: Borrow<A>,
482 T: Borrow<V>,
483 {
484 self.insert_impl(
485 key.borrow(),
486 aug.borrow(),
487 value.borrow(),
488 SetMode::Replace,
489 context,
490 )
491 }
492
493 pub fn add<Q, E, T>(&mut self, key: Q, aug: E, value: T) -> Result<bool, Error>
500 where
501 Q: Borrow<K>,
502 E: Borrow<A>,
503 T: Borrow<V>,
504 {
505 self.add_ext(key, aug, value, Cell::empty_context())
506 }
507
508 pub fn add_ext<Q, E, T>(
511 &mut self,
512 key: Q,
513 aug: E,
514 value: T,
515 context: &dyn CellContext,
516 ) -> Result<bool, Error>
517 where
518 Q: Borrow<K>,
519 E: Borrow<A>,
520 T: Borrow<V>,
521 {
522 self.insert_impl(
523 key.borrow(),
524 aug.borrow(),
525 value.borrow(),
526 SetMode::Add,
527 context,
528 )
529 }
530
531 pub fn remove<Q>(&mut self, key: Q) -> Result<Option<(A, V)>, Error>
534 where
535 Q: Borrow<K>,
536 for<'a> A: Load<'a> + 'static,
537 for<'a> V: Load<'a> + 'static,
538 {
539 match ok!(self.remove_raw_ext(key, Cell::empty_context())) {
540 Some(parts) => {
541 let mut slice = ok!(CellSlice::apply(&parts));
542 let extra = ok!(A::load_from(&mut slice));
543 let value = ok!(V::load_from(&mut slice));
544 Ok(Some((extra, value)))
545 }
546 None => Ok(None),
547 }
548 }
549
550 pub fn remove_raw<Q>(&mut self, key: Q) -> Result<Option<CellSliceParts>, Error>
553 where
554 Q: Borrow<K>,
555 {
556 self.remove_impl(key.borrow(), Cell::empty_context())
557 }
558
559 pub fn remove_raw_ext<Q>(
562 &mut self,
563 key: Q,
564 context: &dyn CellContext,
565 ) -> Result<Option<CellSliceParts>, Error>
566 where
567 Q: Borrow<K>,
568 {
569 self.remove_impl(key.borrow(), context)
570 }
571
572 fn insert_impl(
573 &mut self,
574 key: &K,
575 extra: &A,
576 value: &V,
577 mode: SetMode,
578 context: &dyn CellContext,
579 ) -> Result<bool, Error> {
580 let mut key_builder = CellDataBuilder::new();
581 ok!(key.store_into_data(&mut key_builder));
582 let inserted = ok!(aug_dict_insert(
583 &mut self.dict.root,
584 &mut key_builder.as_data_slice(),
585 K::BITS,
586 extra,
587 value,
588 mode,
589 A::comp_add,
590 context,
591 ));
592
593 if inserted {
594 ok!(self.update_root_extra());
595 }
596
597 Ok(inserted)
598 }
599
600 fn remove_impl(
601 &mut self,
602 key: &K,
603 context: &dyn CellContext,
604 ) -> Result<Option<CellSliceParts>, Error> {
605 let mut key_builder = CellDataBuilder::new();
606 ok!(key.store_into_data(&mut key_builder));
607 let res = ok!(aug_dict_remove_owned(
608 &mut self.dict.root,
609 &mut key_builder.as_data_slice(),
610 K::BITS,
611 false,
612 A::comp_add,
613 context,
614 ));
615
616 if res.is_some() {
617 ok!(self.update_root_extra());
618 }
619
620 Ok(res)
621 }
622
623 pub fn split(&self) -> Result<(Self, Self), Error> {
625 self.split_by_prefix_ext(&Default::default(), Cell::empty_context())
626 }
627
628 pub fn split_ext(&self, context: &dyn CellContext) -> Result<(Self, Self), Error> {
630 self.split_by_prefix_ext(&Default::default(), context)
631 }
632
633 pub fn split_by_prefix(&self, key_prefix: &CellSlice<'_>) -> Result<(Self, Self), Error> {
635 self.split_by_prefix_ext(key_prefix, Cell::empty_context())
636 }
637
638 pub fn split_by_prefix_ext(
640 &self,
641 key_prefix: &CellSlice<'_>,
642 context: &dyn CellContext,
643 ) -> Result<(Self, Self), Error> {
644 let (left, right) = ok!(self.dict.split_by_prefix_ext(key_prefix, context));
645
646 let mut left = Self {
647 dict: left,
648 extra: A::default(),
649 _key: PhantomData,
650 _value: PhantomData,
651 };
652 ok!(left.update_root_extra());
653
654 let mut right = Self {
655 dict: right,
656 extra: A::default(),
657 _key: PhantomData,
658 _value: PhantomData,
659 };
660 ok!(right.update_root_extra());
661
662 Ok((left, right))
663 }
664
665 pub fn merge_with_right_sibling(&self, right: &AugDict<K, A, V>) -> Result<Self, Error> {
667 let dict = self.merge_with_right_sibling_ext(right, Cell::empty_context())?;
668 Ok(dict)
669 }
670
671 pub fn merge_with_right_sibling_ext(
673 &self,
674 right: &AugDict<K, A, V>,
675 context: &dyn CellContext,
676 ) -> Result<Self, Error> {
677 let merged = ok!(aug_dict_merge_siblings(
678 self.dict().root(),
679 right.dict().root(),
680 K::BITS,
681 A::comp_add,
682 context,
683 ));
684
685 let mut res = Self {
686 dict: Dict::from_raw(merged),
687 extra: A::default(),
688 _key: PhantomData,
689 _value: PhantomData,
690 };
691 ok!(res.update_root_extra());
692
693 Ok(res)
694 }
695}
696
697impl<K, A, V> AugDict<K, A, V>
698where
699 K: DictKey,
700{
701 pub fn iter<'a>(&'a self) -> AugIter<'a, K, A, V>
715 where
716 V: Load<'a>,
717 {
718 AugIter::new(self.dict.root())
719 }
720
721 pub fn keys(&'_ self) -> Keys<'_, K> {
734 Keys::new(self.dict.root())
735 }
736}
737
738impl<K, A, V> AugDict<K, A, V>
739where
740 K: DictKey,
741{
742 pub fn values<'a>(&'a self) -> Values<'a, (A, V)>
748 where
749 V: Load<'a>,
750 {
751 Values::new(self.dict.root(), K::BITS)
752 }
753}
754
755impl<K, A, V> AugDict<K, A, V>
756where
757 K: Store + DictKey,
758{
759 pub fn raw_iter(&'_ self) -> RawIter<'_> {
773 RawIter::new(self.dict.root(), K::BITS)
774 }
775
776 pub fn raw_keys(&'_ self) -> RawKeys<'_> {
790 RawKeys::new(self.dict.root(), K::BITS)
791 }
792}
793
794impl<K, A, V> AugDict<K, A, V>
795where
796 K: DictKey,
797{
798 pub fn raw_values(&'_ self) -> RawValues<'_> {
804 RawValues::new(self.dict.root(), K::BITS)
805 }
806}
807
808#[cfg(feature = "serde")]
809impl<K, A, V> serde::Serialize for AugDict<K, A, V>
810where
811 K: serde::Serialize + LoadDictKey,
812 for<'a> A: serde::Serialize + Store + Load<'a>,
813 for<'a> V: serde::Serialize + Load<'a>,
814{
815 fn serialize<S>(&self, serializer: S) -> Result<S::Ok, S::Error>
816 where
817 S: serde::Serializer,
818 {
819 use serde::ser::{Error, SerializeMap};
820
821 #[derive(serde::Serialize)]
822 struct AugDictHelper<'a, K, A, V>
823 where
824 K: serde::Serialize + LoadDictKey,
825 A: serde::Serialize + Store + Load<'a>,
826 V: serde::Serialize + Load<'a>,
827 {
828 #[serde(serialize_with = "serialize_dict_entries")]
829 entires: &'a AugDict<K, A, V>,
830 extra: &'a A,
831 }
832
833 fn serialize_dict_entries<'a, K, A, V, S>(
834 dict: &'a AugDict<K, A, V>,
835 serializer: S,
836 ) -> Result<S::Ok, S::Error>
837 where
838 S: serde::Serializer,
839 K: serde::Serialize + LoadDictKey,
840 A: serde::Serialize + Store + Load<'a>,
841 V: serde::Serialize + Load<'a>,
842 {
843 let mut ser = serializer.serialize_map(None)?;
844 for ref entry in dict.iter() {
845 let (key, extra, value) = match entry {
846 Ok(entry) => entry,
847 Err(e) => return Err(Error::custom(e)),
848 };
849 ok!(ser.serialize_entry(key, &(extra, value)));
850 }
851 ser.end()
852 }
853
854 if serializer.is_human_readable() {
855 AugDictHelper {
856 entires: self,
857 extra: &self.extra,
858 }
859 .serialize(serializer)
860 } else {
861 crate::boc::BocRepr::serialize(self, serializer)
862 }
863 }
864}
865
866pub struct AugIter<'a, K, A, V> {
872 inner: Iter<'a, K, (A, V)>,
873}
874
875impl<K, A, V> Clone for AugIter<'_, K, A, V> {
876 fn clone(&self) -> Self {
877 Self {
878 inner: self.inner.clone(),
879 }
880 }
881}
882
883impl<'a, K, A, V> AugIter<'a, K, A, V>
884where
885 K: DictKey,
886{
887 pub fn new(root: &'a Option<Cell>) -> Self {
889 Self {
890 inner: Iter::new(root),
891 }
892 }
893
894 #[inline]
896 pub fn reversed(mut self) -> Self {
897 self.inner = self.inner.reversed();
898 self
899 }
900
901 #[inline]
903 pub fn signed(mut self) -> Self {
904 self.inner = self.inner.signed();
905 self
906 }
907}
908
909impl<'a, K, A, V> Iterator for AugIter<'a, K, A, V>
910where
911 K: LoadDictKey,
912 (A, V): Load<'a>,
913{
914 type Item = Result<(K, A, V), Error>;
915
916 fn next(&mut self) -> Option<Self::Item> {
917 match self.inner.next()? {
918 Ok((key, (aug, value))) => Some(Ok((key, aug, value))),
919 Err(e) => Some(Err(e)),
920 }
921 }
922}
923
924#[cfg(test)]
925mod tests {
926 use std::collections::VecDeque;
927
928 use anyhow::Context;
929 use tycho_types::models::ShardIdent;
930
931 use super::*;
932 use crate::boc::Boc;
933 use crate::models::{DepthBalanceInfo, ShardAccount, ShardAccounts};
934
935 #[derive(Debug, Default, Load, Store, Eq, PartialEq)]
936 struct OrCmp(bool);
937
938 impl AugDictExtra for OrCmp {
939 fn comp_add(
940 left: &mut CellSlice,
941 right: &mut CellSlice,
942 b: &mut CellBuilder,
943 _: &dyn CellContext,
944 ) -> Result<(), Error> {
945 let left = left.load_bit()?;
946 let right = right.load_bit()?;
947 b.store_bit(left | right)
948 }
949 }
950
951 #[derive(Debug, Default, Load, Store, Eq, PartialEq)]
952 struct SomeValue(u32);
953
954 impl AugDictExtra for SomeValue {
955 fn comp_add(
956 left: &mut CellSlice,
957 right: &mut CellSlice,
958 b: &mut CellBuilder,
959 _: &dyn CellContext,
960 ) -> Result<(), Error> {
961 let left = left.load_u32()?;
962 let right = right.load_u32()?;
963 b.store_u32(left.saturating_add(right))
964 }
965 }
966
967 impl rand9::distr::Distribution<SomeValue> for rand9::distr::StandardUniform {
968 #[inline]
969 fn sample<R: rand9::Rng + ?Sized>(&self, rng: &mut R) -> SomeValue {
970 SomeValue(rng.random())
971 }
972 }
973
974 #[derive(Debug, Default, Load, Store, Eq, PartialEq)]
975 struct ValueWithCell(u32, Cell);
976
977 impl ValueWithCell {
978 fn new(num: u32, cell: u32) -> Self {
979 Self(num, CellBuilder::build_from(cell).unwrap())
980 }
981 }
982
983 impl AugDictExtra for ValueWithCell {
984 fn comp_add(
985 left: &mut CellSlice,
986 right: &mut CellSlice,
987 b: &mut CellBuilder,
988 ctx: &dyn CellContext,
989 ) -> Result<(), Error> {
990 let left_num = left.load_u32()?;
1000 let left_cell = left.load_reference_as_slice()?.load_u32()?;
1001
1002 let right_num = right.load_u32()?;
1003 let right_cell = right.load_reference_as_slice()?.load_u32()?;
1004
1005 ValueWithCell::new(
1006 left_num.saturating_add(right_num),
1007 left_cell.saturating_add(right_cell),
1008 )
1009 .store_into(b, ctx)
1010 }
1011 }
1012
1013 #[test]
1014 fn dict_set() {
1015 let mut dict = AugDict::<u32, OrCmp, u16>::new();
1016 assert_eq!(*dict.root_extra(), OrCmp(false));
1017
1018 dict.set(123, OrCmp(false), 0xffff).unwrap();
1019 assert_eq!(dict.get(123).unwrap(), Some((OrCmp(false), 0xffff)));
1020 assert_eq!(*dict.root_extra(), OrCmp(false));
1021
1022 dict.set(123, OrCmp(true), 0xcafe).unwrap();
1023 assert_eq!(dict.get(123).unwrap(), Some((OrCmp(true), 0xcafe)));
1024 assert_eq!(*dict.root_extra(), OrCmp(true));
1025 }
1026
1027 #[test]
1028 fn dict_set_complex() {
1029 let mut dict = AugDict::<u32, OrCmp, u32>::new();
1030 assert_eq!(*dict.root_extra(), OrCmp(false));
1031
1032 for i in 0..520 {
1033 dict.set(i, OrCmp(true), 123).unwrap();
1034 }
1035 assert_eq!(*dict.root_extra(), OrCmp(true));
1036 }
1037
1038 #[test]
1039 fn dict_replace() {
1040 let mut dict = AugDict::<u32, OrCmp, u16>::new();
1041 assert_eq!(*dict.root_extra(), OrCmp(false));
1042 dict.replace(123, OrCmp(false), 0xff).unwrap();
1043 assert!(!dict.contains_key(123).unwrap());
1044 assert_eq!(*dict.root_extra(), OrCmp(false));
1045
1046 dict.set(123, OrCmp(false), 0xff).unwrap();
1047 assert_eq!(dict.get(123).unwrap(), Some((OrCmp(false), 0xff)));
1048 assert_eq!(*dict.root_extra(), OrCmp(false));
1049
1050 dict.replace(123, OrCmp(true), 0xaa).unwrap();
1051 assert_eq!(dict.get(123).unwrap(), Some((OrCmp(true), 0xaa)));
1052 assert_eq!(*dict.root_extra(), OrCmp(true));
1053 }
1054
1055 #[test]
1056 fn dict_add() {
1057 let mut dict = AugDict::<u32, OrCmp, u16>::new();
1058 assert_eq!(*dict.root_extra(), OrCmp(false));
1059
1060 dict.add(123, OrCmp(false), 0x12).unwrap();
1061 assert_eq!(dict.get(123).unwrap(), Some((OrCmp(false), 0x12)));
1062 assert_eq!(*dict.root_extra(), OrCmp(false));
1063
1064 dict.add(123, OrCmp(true), 0x11).unwrap();
1065 assert_eq!(dict.get(123).unwrap(), Some((OrCmp(false), 0x12)));
1066 assert_eq!(*dict.root_extra(), OrCmp(false));
1067 }
1068
1069 #[test]
1070 fn dict_remove() {
1071 let mut dict = AugDict::<u32, OrCmp, u32>::new();
1072 assert_eq!(*dict.root_extra(), OrCmp(false));
1073
1074 for i in 0..10 {
1075 assert!(dict.set(i, OrCmp(i % 2 == 0), i).unwrap());
1076 }
1077 assert_eq!(*dict.root_extra(), OrCmp(true));
1078
1079 let mut check_remove = |n: u32, expected: Option<(OrCmp, u32)>| -> anyhow::Result<()> {
1080 let removed = dict.remove(n).context("Failed to remove")?;
1081 anyhow::ensure!(removed == expected);
1082 Ok(())
1083 };
1084
1085 check_remove(0, Some((OrCmp(true), 0))).unwrap();
1086
1087 check_remove(4, Some((OrCmp(true), 4))).unwrap();
1088
1089 check_remove(9, Some((OrCmp(false), 9))).unwrap();
1090 check_remove(9, None).unwrap();
1091
1092 check_remove(5, Some((OrCmp(false), 5))).unwrap();
1093 check_remove(5, None).unwrap();
1094
1095 check_remove(100, None).unwrap();
1096
1097 check_remove(1, Some((OrCmp(false), 1))).unwrap();
1098 check_remove(2, Some((OrCmp(true), 2))).unwrap();
1099 check_remove(3, Some((OrCmp(false), 3))).unwrap();
1100 check_remove(6, Some((OrCmp(true), 6))).unwrap();
1101 check_remove(7, Some((OrCmp(false), 7))).unwrap();
1102 check_remove(8, Some((OrCmp(true), 8))).unwrap();
1103
1104 assert!(dict.is_empty());
1105 }
1106
1107 #[test]
1108 fn dict_iter() {
1109 let mut dict = AugDict::<u32, SomeValue, u32>::new();
1110 assert_eq!(*dict.root_extra(), SomeValue(0));
1111
1112 let mut expected_extra = 0;
1113 for i in 0..10 {
1114 expected_extra += i;
1115 dict.set(i, SomeValue(i), 9 - i).unwrap();
1116 }
1117 assert_eq!(*dict.root_extra(), SomeValue(expected_extra));
1118
1119 let size = dict.values().count();
1120 assert_eq!(size, 10);
1121
1122 for (i, entry) in dict.iter().enumerate() {
1123 let (key, aug, value) = entry.unwrap();
1124 assert_eq!(SomeValue(key), aug);
1125 assert_eq!(key, i as u32);
1126 assert_eq!(value, 9 - i as u32);
1127 }
1128 }
1129
1130 #[cfg(feature = "models")]
1131 #[test]
1132 fn aug_test() {
1133 use crate::models::{AccountBlock, CurrencyCollection};
1134 use crate::prelude::Boc;
1135
1136 let boc = Boc::decode(include_bytes!("./tests/account_blocks_aug_dict.boc")).unwrap();
1137
1138 let original_dict = boc
1139 .parse::<AugDict<HashBytes, CurrencyCollection, AccountBlock>>()
1140 .unwrap();
1141
1142 let mut data = Vec::new();
1143 for entry in original_dict.iter() {
1144 data.push(entry.unwrap());
1145 }
1146 data.reverse();
1147
1148 let mut new_dict: AugDict<HashBytes, CurrencyCollection, AccountBlock> = AugDict::new();
1149 for (key, aug, value) in data.iter() {
1150 new_dict.add(key, aug, value).unwrap();
1151 }
1152 assert_eq!(new_dict.root_extra(), original_dict.root_extra());
1153
1154 let serialized = CellBuilder::build_from(&new_dict).unwrap();
1155 assert_eq!(serialized.repr_hash(), boc.repr_hash());
1156
1157 for (key, _, _) in data.iter() {
1158 new_dict.remove(key).unwrap();
1159 }
1160 assert!(new_dict.is_empty());
1161 assert_eq!(new_dict.root_extra(), &CurrencyCollection::ZERO);
1162 }
1163
1164 #[test]
1165 fn build_from_array() {
1166 for entries in [
1167 &[
1168 (0u32, SomeValue(123), 1u32),
1169 (1, SomeValue(10), 2),
1170 (2, SomeValue(20), 4),
1171 (2, SomeValue(20), 3),
1172 (3, SomeValue(40), 4),
1173 (4, SomeValue(50), 5),
1174 ][..],
1175 &[
1176 (534837844, SomeValue(331123), 3117028142),
1177 (1421713188, SomeValue(5345345), 3155891450),
1178 (1526242096, SomeValue(567567), 2789399854),
1179 (1971086295, SomeValue(5345), 1228713494),
1180 (4258889371, SomeValue(4956495), 3256452222),
1181 ],
1182 ] {
1183 let result = AugDict::<u32, SomeValue, u32>::try_from_sorted_slice(entries).unwrap();
1184
1185 let mut dict = AugDict::<u32, SomeValue, u32>::new();
1186 for (k, a, v) in entries {
1187 dict.add(k, a, v).unwrap();
1188 }
1189
1190 println!("{}", result.dict.root.as_ref().unwrap().display_tree());
1191 println!(
1192 "BOC: {}",
1193 crate::boc::BocRepr::encode_base64(&result).unwrap()
1194 );
1195
1196 assert_eq!(result, dict);
1197 }
1198 }
1199
1200 #[test]
1201 fn compare_sorted_res() -> anyhow::Result<()> {
1202 let mut dict = AugDict::<u32, SomeValue, u64>::new();
1203 dict.add(268445184, SomeValue(269488144), 18446744073693827088)?;
1204 dict.add(4294934527, SomeValue(4294967295), 1224979098644774911)?;
1205
1206 let mut other = AugDict::<u32, SomeValue, u64>::try_from_sorted_slice(&[
1207 (268445184, SomeValue(269488144), 18446744073693827088),
1208 (4294934527, SomeValue(4294967295), 1224979098644774911),
1209 ])?;
1210 assert_eq!(other, dict);
1211
1212 other.remove(0)?;
1213 assert_eq!(other, dict);
1214
1215 other.modify_with_sorted_iter([(0, None)])?;
1216 assert_eq!(other, dict);
1217
1218 Ok(())
1219 }
1220
1221 #[test]
1222 fn modify_aug_with_cells() -> anyhow::Result<()> {
1223 let mut dict = AugDict::<u32, ValueWithCell, u64>::new();
1224 dict.add(
1225 16729856,
1226 ValueWithCell::new(1111, 123),
1227 18381441879129409280,
1228 )?;
1229 dict.add(
1230 3607101952,
1231 ValueWithCell::new(2060965847, 234),
1232 8851780914645041664,
1233 )?;
1234
1235 let mut other = AugDict::<u32, ValueWithCell, u64>::try_from_sorted_slice(&[
1236 (
1237 16729856,
1238 ValueWithCell::new(1111, 123),
1239 18381441879129409280,
1240 ),
1241 (
1242 3607101952,
1243 ValueWithCell::new(2060965847, 234),
1244 8851780914645041664,
1245 ),
1246 ])?;
1247 assert_eq!(other, dict);
1248
1249 println!(
1250 "INITIAL: {:?}",
1251 dict.dict.root.as_ref().map(Boc::encode_base64),
1252 );
1253
1254 dict.set(0, ValueWithCell::new(0, 0), 0)?;
1255 println!(
1256 "TARGET: {:?}",
1257 dict.dict.root.as_ref().map(Boc::encode_base64),
1258 );
1259
1260 other.modify_with_sorted_iter([(0, Some((ValueWithCell::new(0, 0), 0)))])?;
1261 println!(
1262 "RESULT: {:?}",
1263 other.dict.root.as_ref().map(Boc::encode_base64),
1264 );
1265 assert_eq!(other, dict);
1266
1267 Ok(())
1268 }
1269
1270 #[test]
1271 fn modify_aug_with_cells_remove() -> anyhow::Result<()> {
1272 let mut dict = AugDict::<u32, ValueWithCell, u64>::new();
1273 dict.add(66024, ValueWithCell::new(0, 123), 4108413175295410176)?;
1274 dict.add(
1275 2575203966,
1276 ValueWithCell::new(67108922, 234),
1277 16710326059140383999,
1278 )?;
1279 dict.add(
1280 3907577831,
1281 ValueWithCell::new(3907578088, 345),
1282 144121978453491944,
1283 )?;
1284
1285 let mut other = AugDict::<u32, ValueWithCell, u64>::try_from_sorted_slice(&[
1286 (66024, ValueWithCell::new(0, 123), 4108413175295410176),
1287 (
1288 2575203966,
1289 ValueWithCell::new(67108922, 234),
1290 16710326059140383999,
1291 ),
1292 (
1293 3907577831,
1294 ValueWithCell::new(3907578088, 345),
1295 144121978453491944,
1296 ),
1297 ])?;
1298 assert_eq!(other, dict);
1299
1300 println!(
1301 "INITIAL: {:?}",
1302 dict.dict.root.as_ref().map(Boc::encode_base64),
1303 );
1304
1305 dict.remove(0)?;
1306 dict.remove(71)?;
1307 assert_eq!(other, dict);
1308
1309 other.modify_with_sorted_iter([(0, None), (71, None)])?;
1310 println!(
1311 "RESULT: {:?}",
1312 other.dict.root.as_ref().map(Boc::encode_base64),
1313 );
1314 assert_eq!(other, dict);
1315
1316 Ok(())
1317 }
1318
1319 #[test]
1320 fn build_from_any_array() {
1321 for _ in 0..100 {
1322 let n = 1 + rand9::random::<u32>() % 1000;
1323 let mut entries = (0..n)
1324 .map(|_| {
1325 (
1326 rand9::random::<u32>(),
1327 rand9::random::<SomeValue>(),
1328 rand9::random::<u32>(),
1329 )
1330 })
1331 .collect::<Vec<_>>();
1332 entries.sort_by_key(|(k, _, _)| *k);
1333
1334 let built_from_dict =
1335 AugDict::<u32, SomeValue, u32>::try_from_sorted_slice(&entries).unwrap();
1336
1337 let mut dict = AugDict::<u32, SomeValue, u32>::new();
1338 for (k, a, v) in entries {
1339 dict.add(k, a, v).unwrap();
1340 }
1341
1342 assert_eq!(built_from_dict, dict);
1345 }
1346 }
1347
1348 #[test]
1349 fn search_by_lt() {
1350 #[derive(Debug, Default, Clone, Copy, PartialEq, Eq, PartialOrd, Ord, Store, Load)]
1351 struct MaxValue(u64);
1352
1353 impl AugDictExtra for MaxValue {
1354 fn comp_add(
1355 left: &mut CellSlice,
1356 right: &mut CellSlice,
1357 b: &mut CellBuilder,
1358 _: &dyn CellContext,
1359 ) -> Result<(), Error> {
1360 let left = left.load_u64()?;
1361 let right = right.load_u64()?;
1362 b.store_u64(left.max(right))
1363 }
1364 }
1365
1366 let mut items = AugDict::<u32, MaxValue, u32>::new();
1367 items.set(0, MaxValue(100), 123).unwrap();
1368 items.set(2, MaxValue(150), 234).unwrap();
1369 items.set(4, MaxValue(200), 345).unwrap();
1370 items.set(6, MaxValue(350), 456).unwrap();
1371 items.set(7, MaxValue(300), 567).unwrap();
1372 items.set(8, MaxValue(250), 678).unwrap();
1373
1374 let highest = items.find_by_extra(std::cmp::Ordering::Greater).unwrap();
1376 assert_eq!(highest, Some((6, MaxValue(350), 456)));
1377 }
1378
1379 #[test]
1380 fn split_merge_aug_test() -> anyhow::Result<()> {
1381 let mut dict = AugDict::<u32, OrCmp, u32>::new();
1382 dict.add(1, OrCmp(true), 1)?;
1383 dict.add(2, OrCmp(true), 1)?;
1384 dict.add(3, OrCmp(true), 1)?;
1385 dict.add(u32::MAX - 2, OrCmp(false), 4)?;
1386 dict.add(u32::MAX - 1, OrCmp(false), 5)?;
1387 dict.add(u32::MAX, OrCmp(false), 6)?;
1388
1389 let (d1, d2) = dict.split()?;
1390
1391 let merged = d1.merge_with_right_sibling(&d2)?;
1392 for i in merged.iter() {
1393 let _ = i?;
1394 }
1395 assert_eq!(dict, merged);
1396
1397 Ok(())
1398 }
1399
1400 #[test]
1401 fn merge_with_none() -> anyhow::Result<()> {
1402 let cell = Boc::decode_base64(
1403 "te6ccgECCgEAAcMAAQ+BlrzEHpAAEAEBoaACN33l61Vk62GrjymKAv197LmrqqmfcDpXYIKjXocJzABlrzEHpAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAABAICc8/xG77y9aqydbDVx5TFAX6+9lzV1VTPuB0rsEFRr0OE5gIQgkNAAAAAAAAAAAAAAAABlrzEHpAAE0AEAwBQiSKga9Z+zeO4A1bGS5OIEoMIyhKQn+Fzzir2sgDX9BQAAAAAAAAAAAEU/wD0pBP0vPLICwUCASAJBgLm8nHXAQHAAPJ6gwjXGO1E0IMH1wHXCz/I+CjPFiPPFsn5AANx1wEBwwCagwfXAVETuvLgZN6AQNcBgCDXAYAg1wFUFnX5EPKo+CO78nlmvvgjgQcIoIED6KhSILyx8nQCIIIQTO5kbLrjDwHIy//LP8ntVAgHAD6CEBaePhG6jhH4AAKTINdKl3jXAdQC+wDo0ZMy8jziAJgwAtdM0PpAgwbXAXHXAXjXAddM+ABwgBAEqgIUscjLBVAFzxZQA/oCy2ki0CHPMSHXSaCECbmYM3ABywBYzxaXMHEBywASzOLJAfsAAATSMA==",
1404 )?;
1405 let cell2 = Boc::decode_base64("te6ccgEBAQEABAAAAwAQ")?;
1406
1407 let accounts = ShardAccounts::load_from(&mut cell.as_slice()?)?;
1408 let accounts2 = ShardAccounts::load_from(&mut cell2.as_slice()?)?;
1409
1410 for i in accounts.iter() {
1411 let _ = i?;
1412 }
1413
1414 for i in accounts2.iter() {
1415 let _ = i?;
1416 }
1417
1418 let merged = accounts.merge_with_right_sibling(&accounts2)?;
1419 let merged2 = accounts2.merge_with_right_sibling(&accounts)?;
1420
1421 assert_eq!(merged, merged2);
1422 Ok(())
1423 }
1424
1425 #[test]
1426 fn split_merge_multiple() -> anyhow::Result<()> {
1427 let cell = Boc::decode_base64(
1428 "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",
1429 )?;
1430 let accounts = ShardAccounts::load_from(&mut cell.as_slice()?)?;
1431 let mut shards = BTreeMap::new();
1432 let shard = ShardIdent::new(-1, u64::from_str_radix("8000000000000000", 16)?).unwrap();
1433 split_shard_accounts(&shard, &accounts, 3, &mut shards)?;
1434 let merged = merge(shards)?;
1435 assert_eq!(accounts, merged);
1436 Ok(())
1437 }
1438
1439 fn merge(
1440 shard_accounts: BTreeMap<u64, ShardAccounts>,
1441 ) -> anyhow::Result<AugDict<HashBytes, DepthBalanceInfo, ShardAccount>> {
1442 let shard_accounts = {
1443 let mut stack = VecDeque::with_capacity(16);
1444 for accounts in shard_accounts.values() {
1445 for account in accounts.iter() {
1446 let _ = account?;
1447 }
1448 stack.push_back(accounts);
1449 }
1450
1451 let d2 = stack[0].merge_with_right_sibling(stack[1])?;
1452 let d1 = stack[2].merge_with_right_sibling(stack[3])?;
1453 let d3 = stack[4].merge_with_right_sibling(stack[5])?;
1454 let d4 = stack[6].merge_with_right_sibling(stack[7])?;
1455
1456 let x1 = d2.merge_with_right_sibling(&d1)?;
1457 let x2 = d3.merge_with_right_sibling(&d4)?;
1458 x1.merge_with_right_sibling(&x2)?
1459 };
1460 Ok(shard_accounts)
1461 }
1462
1463 fn split_shard_accounts(
1464 shard: &ShardIdent,
1465 accounts: &ShardAccounts,
1466 depth: u8,
1467 shards: &mut BTreeMap<u64, ShardAccounts>,
1468 ) -> anyhow::Result<()> {
1469 fn split_shard_accounts_impl(
1470 shard: &ShardIdent,
1471 accounts: &ShardAccounts,
1472 depth: u8,
1473 shards: &mut BTreeMap<u64, ShardAccounts>,
1474 builder: &mut CellBuilder,
1475 ) -> anyhow::Result<()> {
1476 let (left_shard_ident, right_shard_ident) = 'split: {
1477 if depth > 0 {
1478 if let Some((left, right)) = shard.split() {
1479 break 'split (left, right);
1480 }
1481 }
1482 shards.insert(shard.prefix(), accounts.clone());
1483 return Ok(());
1484 };
1485
1486 let (left_accounts, right_accounts) = {
1487 builder.clear_bits();
1488 let prefix_len = shard.prefix_len();
1489 if prefix_len > 0 {
1490 builder.store_uint(shard.prefix() >> (64 - prefix_len), prefix_len)?;
1491 }
1492
1493 let (a1, a2) = accounts.split_by_prefix(&builder.as_data_slice())?;
1494 (a1, a2)
1495 };
1496
1497 split_shard_accounts_impl(
1498 &left_shard_ident,
1499 &left_accounts,
1500 depth - 1,
1501 shards,
1502 builder,
1503 )?;
1504 split_shard_accounts_impl(
1505 &right_shard_ident,
1506 &right_accounts,
1507 depth - 1,
1508 shards,
1509 builder,
1510 )
1511 }
1512
1513 split_shard_accounts_impl(shard, accounts, depth, shards, &mut CellBuilder::new())
1514 }
1515}