Skip to main content

inc_complete/
accumulate.rs

1use dashmap::DashMap;
2use serde::{Deserialize, Serialize};
3
4use crate::Cell;
5
6/// An accumulator is a collection which can accumulate a given cell key associated with multiple
7/// values of a given type. `Accumulator<MyItem>` is an example of such a type.
8///
9/// This is most often a hashmap or similar map
10pub trait Accumulate<Item> {
11    /// Push an item to the context of the given cell
12    fn accumulate(&self, cell: Cell, item: Item);
13
14    /// Retrieve all items associated with the given cells
15    fn get_accumulated<Items>(&self, cells: &[Cell]) -> Items
16        where Items: FromIterator<Item>;
17}
18
19pub struct Accumulator<Item> {
20    map: DashMap<Cell, Vec<Item>>,
21}
22
23impl<T> Default for Accumulator<T> {
24    fn default() -> Self {
25        Self { map: Default::default() }
26    }
27}
28
29impl<Item: Clone> Accumulate<Item> for Accumulator<Item> {
30    fn accumulate(&self, cell: Cell, item: Item) {
31        self.map.accumulate(cell, item);
32    }
33
34    fn get_accumulated<Items>(&self, cells: &[Cell]) -> Items where
35        Items: FromIterator<Item>
36    {
37        self.map.get_accumulated(cells)
38    }
39}
40
41impl<Item: Clone> Accumulate<Item> for DashMap<Cell, Vec<Item>> {
42    fn accumulate(&self, cell: Cell, item: Item) {
43        self.entry(cell).or_default().push(item);
44    }
45
46    fn get_accumulated<Items>(&self, cells: &[Cell]) -> Items
47        where Items: FromIterator<Item>
48    {
49        let iter = cells.iter().filter_map(|cell| {
50            self.get(cell).map(|items| items.clone())
51        }).flatten();
52
53        FromIterator::from_iter(iter)
54    }
55}
56
57impl<Item: Serialize + Clone> Serialize for Accumulator<Item> {
58    fn serialize<S>(&self, serializer: S) -> Result<S::Ok, S::Error> where
59        S: serde::Serializer
60    {
61        let vec: Vec<(Cell, Vec<Item>)> = self.map.iter().map(|entry| {
62            (*entry.key(), entry.value().clone())
63        }).collect();
64
65        vec.serialize(serializer)
66    }
67}
68
69impl<'de, Item: Deserialize<'de>> Deserialize<'de> for Accumulator<Item> {
70    fn deserialize<D>(deserializer: D) -> Result<Self, D::Error> where
71        D: serde::Deserializer<'de>
72    {
73        let vec: Vec<(Cell, Vec<Item>)> = Deserialize::deserialize(deserializer)?;
74        let map = vec.into_iter().collect();
75        Ok(Accumulator { map })
76    }
77}