Skip to main content

code_moniker_workspace/snapshot/inventory/
set.rs

1use roaring::RoaringBitmap;
2
3use super::SymbolOrdinal;
4
5// A bitmap-backed value object intentionally offers the set algebra used by
6// linkage and rules; cohesion metrics cannot infer that all methods share the
7// wrapped RoaringBitmap through its domain operations.
8// code-moniker: ignore[smell-god-type-local-metrics]
9#[derive(Clone, Debug, Default, Eq, PartialEq)]
10pub struct SymbolSet {
11	bitmap: RoaringBitmap,
12}
13
14impl SymbolSet {
15	pub fn new() -> Self {
16		Self {
17			bitmap: RoaringBitmap::new(),
18		}
19	}
20
21	pub fn insert(&mut self, symbol: SymbolOrdinal) -> bool {
22		self.bitmap.insert(symbol.raw())
23	}
24
25	pub fn remove(&mut self, symbol: SymbolOrdinal) -> bool {
26		self.bitmap.remove(symbol.raw())
27	}
28
29	pub fn contains(&self, symbol: SymbolOrdinal) -> bool {
30		self.bitmap.contains(symbol.raw())
31	}
32
33	pub fn intersect_with(&mut self, other: &Self) {
34		self.bitmap &= &other.bitmap;
35	}
36
37	pub fn union_with(&mut self, other: &Self) {
38		self.bitmap |= &other.bitmap;
39	}
40
41	pub fn remove_all(&mut self, other: &Self) {
42		self.bitmap -= &other.bitmap;
43	}
44
45	pub fn intersection(&self, other: &Self) -> Self {
46		let mut result = self.clone();
47		result.intersect_with(other);
48		result
49	}
50
51	pub fn union(&self, other: &Self) -> Self {
52		let mut result = self.clone();
53		result.union_with(other);
54		result
55	}
56
57	pub fn difference(&self, other: &Self) -> Self {
58		let mut result = self.clone();
59		result.remove_all(other);
60		result
61	}
62
63	pub fn from_symbol(symbol: SymbolOrdinal) -> Self {
64		let mut set = Self::new();
65		set.insert(symbol);
66		set
67	}
68
69	pub fn is_empty(&self) -> bool {
70		self.bitmap.is_empty()
71	}
72
73	pub fn serialized_size(&self) -> usize {
74		self.bitmap.serialized_size()
75	}
76
77	pub(super) fn estimated_heap_bytes(&self) -> usize {
78		self.bitmap.serialized_size()
79	}
80
81	pub fn single(&self) -> Option<SymbolOrdinal> {
82		(self.len() == 1).then(|| self.iter().next()).flatten()
83	}
84
85	pub fn len(&self) -> usize {
86		let len = self.bitmap.len();
87		assert!(
88			usize::try_from(len).is_ok(),
89			"symbol set length exceeds usize"
90		);
91		len as usize
92	}
93
94	pub fn iter(&self) -> impl Iterator<Item = SymbolOrdinal> + '_ {
95		self.bitmap.iter().map(SymbolOrdinal)
96	}
97}
98
99impl FromIterator<SymbolOrdinal> for SymbolSet {
100	fn from_iter<T: IntoIterator<Item = SymbolOrdinal>>(iter: T) -> Self {
101		let mut set = Self::new();
102		for symbol in iter {
103			set.insert(symbol);
104		}
105		set
106	}
107}