iron_ingot/functions/
collections.rs1use crate::any;
2
3use std::{
4 borrow::Cow,
5 cmp::Ordering::{Equal, Greater, Less},
6 collections::{HashMap, HashSet},
7 hash::Hash,
8};
9
10pub trait PropChecker {
11 fn is_unique(&self) -> bool;
13}
14
15impl<T: Eq + Hash> PropChecker for [T] {
16 fn is_unique(&self) -> bool {
17 let mut unique = HashSet::with_capacity(self.len());
18 self.iter().all(|value| unique.insert(value))
19 }
20}
21
22pub fn min<T, R: Ord>(array: &[T], mut get_value: impl FnMut(&T, usize) -> R) -> Cow<[&T]> {
31 let mut min_value: Option<R> = None;
32 let mut result = vec![];
33 for (i, any) in array.iter().enumerate() {
34 let value = get_value(any, i);
35 if let Some(unwrapped_min_value) = &min_value {
36 match value.cmp(unwrapped_min_value) {
37 Greater => continue,
38 Less => {
39 min_value = Some(value);
40 result = vec![any];
41 }
42 Equal => result.push(any),
43 }
44 } else {
45 min_value = Some(value);
46 result = vec![any];
47 }
48 }
49 result.into()
50}
51
52pub fn max<T, R: Ord>(array: &[T], mut get_value: impl FnMut(&T, usize) -> R) -> Cow<[&T]> {
61 let mut max_value: Option<R> = None;
62 let mut result = vec![];
63 for (i, any) in array.iter().enumerate() {
64 let value = get_value(any, i);
65 if let Some(unwrapped_max_value) = &max_value {
66 match value.cmp(unwrapped_max_value) {
67 Less => continue,
68 Greater => {
69 max_value = Some(value);
70 result = vec![any];
71 }
72 Equal => result.push(any),
73 }
74 } else {
75 max_value = Some(value);
76 result = vec![any];
77 }
78 }
79 result.into()
80}
81
82pub fn into_slice<'a, K: Eq + Hash, V: crate::Hash<Part = &'a K>>(
88 map: HashMap<&'a K, &'a [&V]>,
89) -> Cow<'a, [&'a V]> {
90 let mut result = Vec::with_capacity(map.len());
91 let mut is_exists = HashMap::with_capacity(map.len());
92 for &anys in map.values() {
93 for &any in anys {
94 let hash = any.hash();
95 if is_exists.get(&hash).is_some() {
96 continue;
97 }
98 result.push(any);
99 is_exists.entry(hash).or_insert(true);
100 }
101 }
102 result.into()
103}
104
105pub fn into_map<'a, K: Eq + Hash, V: crate::Hash<Part = &'a K> + Eq + Hash>(
111 slice: &'a [&V],
112) -> HashMap<&'a K, Cow<'a, [&'a V]>> {
113 debug_assert!(
114 slice.is_unique(),
115 "slice must not contains duplicate objects!"
116 );
117 let mut result = HashMap::<_, Vec<_>>::new();
118 for &any in slice {
119 for &hash_part in &*any::hash::Hash::hash(any) {
120 result.entry(hash_part).or_insert(Vec::new()).push(any);
121 }
122 }
123 result
124 .into_iter()
125 .map(|(key, value)| (key, value.into()))
126 .collect()
127}
128
129pub fn add<'a, K: Eq + Hash, V: crate::Hash<Part = &'a K>>(
137 am: HashMap<&'a K, &'a [&V]>,
138 bm: HashMap<&'a K, &'a [&V]>,
139) -> HashMap<&'a K, Cow<'a, [&'a V]>> {
140 let mut rm = HashMap::<_, Vec<_>>::with_capacity(am.len() + bm.len());
141 let mut is_exists = HashMap::with_capacity(am.len());
142 for &a in into_slice(am).iter() {
143 let hash = a.hash();
144 for &hash_part in hash.iter() {
145 rm.entry(hash_part).or_insert(Vec::new()).push(a);
146 }
147 is_exists.entry(hash).or_insert(true);
148 }
149 for &b in into_slice(bm).iter() {
150 let hash = b.hash();
151 if is_exists.get(&hash).is_some() {
152 continue;
153 }
154 for &hash_part in hash.iter() {
155 rm.entry(hash_part).or_insert(Vec::new()).push(b);
156 }
157 }
158 rm.into_iter()
159 .map(|(key, value)| (key, value.into()))
160 .collect()
161}
162
163pub fn sub<'a, K: Eq + Hash, V: crate::Hash<Part = &'a K>>(
171 am: HashMap<&'a K, &'a [&V]>,
172 bm: HashMap<&'a K, &'a [&V]>,
173) -> HashMap<&'a K, Cow<'a, [&'a V]>> {
174 let mut rm = HashMap::<_, Vec<_>>::with_capacity(am.len());
175 let mut is_exists = HashMap::with_capacity(bm.len());
176 for &b in into_slice(bm).iter() {
177 is_exists.entry(b.hash()).or_insert(true);
178 }
179 for &a in into_slice(am).iter() {
180 let hash = a.hash();
181 if is_exists.get(&hash).is_some() {
182 continue;
183 }
184 for &hash_part in hash.iter() {
185 rm.entry(hash_part).or_insert(Vec::new()).push(a);
186 }
187 }
188 rm.into_iter()
189 .map(|(key, value)| (key, value.into()))
190 .collect()
191}