1use crate::collections::HashMap;
2use crate::references::reference::KeyNotFoundError;
3use crate::std_random::RandomState;
4use crate::stdlib::borrow::Cow;
5use crate::stdlib::format;
6use crate::stdlib::string::String;
7use crate::stdlib::vec::Vec;
8use crate::traits::structural_eq::StructuralEq;
9use crate::values::core_value::CoreValue;
10use crate::values::value::Value;
11use crate::values::value_container::{ValueContainer, ValueKey};
12use core::fmt::{self, Display};
13use core::hash::{Hash, Hasher};
14use core::prelude::rust_2024::*;
15use core::result::Result;
16use indexmap::IndexMap;
17
18#[derive(Clone, Debug, Eq, PartialEq)]
19pub enum Map {
20 Dynamic(IndexMap<ValueContainer, ValueContainer, RandomState>),
22 Fixed(Vec<(ValueContainer, ValueContainer)>),
24 Structural(Vec<(String, ValueContainer)>), }
27
28#[derive(Debug, Clone, PartialEq)]
29pub enum MapAccessError {
30 KeyNotFound(KeyNotFoundError),
31 Immutable,
32}
33
34impl Display for MapAccessError {
35 fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
36 match self {
37 MapAccessError::KeyNotFound(err) => {
38 core::write!(f, "{}", err)
39 }
40 MapAccessError::Immutable => {
41 core::write!(f, "Map is immutable")
42 }
43 }
44 }
45}
46
47impl Default for Map {
48 fn default() -> Self {
49 Map::Dynamic(IndexMap::default())
50 }
51}
52
53impl Map {
54 pub fn new(
55 entries: IndexMap<ValueContainer, ValueContainer, RandomState>,
56 ) -> Self {
57 Map::Dynamic(entries)
58 }
59
60 pub fn is_structural(&self) -> bool {
61 core::matches!(self, Map::Structural(_))
62 }
63
64 pub fn has_fixed_size(&self) -> bool {
65 core::matches!(self, Map::Fixed(_) | Map::Structural(_))
66 }
67
68 pub fn size(&self) -> usize {
69 match self {
70 Map::Dynamic(map) => map.len(),
71 Map::Fixed(vec) => vec.len(),
72 Map::Structural(vec) => vec.len(),
73 }
74 }
75
76 pub fn is_empty(&self) -> bool {
77 self.size() == 0
78 }
79
80 pub fn get<'a>(
83 &self,
84 key: impl Into<ValueKey<'a>>,
85 ) -> Result<&ValueContainer, KeyNotFoundError> {
86 let key = key.into();
87 match self {
88 Map::Dynamic(map) => key.with_value_container(|key| map.get(key)),
89 Map::Fixed(vec) => key.with_value_container(|key| {
90 vec.iter().find(|(k, _)| k == key).map(|(_, v)| v)
91 }),
92 Map::Structural(vec) => {
93 if let Some(string) = key.try_as_text() {
95 vec.iter().find(|(k, _)| k == string).map(|(_, v)| v)
96 } else {
97 None
98 }
99 }
100 }
101 .ok_or_else(|| KeyNotFoundError { key: key.into() })
102 }
103
104 pub fn has<'a>(&self, key: impl Into<ValueKey<'a>>) -> bool {
106 match self {
107 Map::Dynamic(map) => {
108 key.into().with_value_container(|key| map.contains_key(key))
109 }
110 Map::Fixed(vec) => key
111 .into()
112 .with_value_container(|key| vec.iter().any(|(k, _)| k == key)),
113 Map::Structural(vec) => {
114 if let Some(string) = key.into().try_as_text() {
116 vec.iter().any(|(k, _)| k == string)
117 } else {
118 false
119 }
120 }
121 }
122 }
123
124 pub fn delete<'a>(
126 &mut self,
127 key: impl Into<ValueKey<'a>>,
128 ) -> Result<ValueContainer, MapAccessError> {
129 let key = key.into();
130 match self {
131 Map::Dynamic(map) => key.with_value_container(|key| {
132 map.shift_remove(key).ok_or_else(|| {
133 MapAccessError::KeyNotFound(KeyNotFoundError {
134 key: key.clone(),
135 })
136 })
137 }),
138 Map::Fixed(_) | Map::Structural(_) => {
139 Err(MapAccessError::Immutable)
140 }
141 }
142 }
143
144 pub fn clear(&mut self) -> Result<(), MapAccessError> {
146 match self {
147 Map::Dynamic(map) => {
148 map.clear();
149 Ok(())
150 }
151 Map::Fixed(_) | Map::Structural(_) => {
152 Err(MapAccessError::Immutable)
153 }
154 }
155 }
156
157 pub(crate) fn set<'a>(
159 &mut self,
160 key: impl Into<ValueKey<'a>>,
161 value: impl Into<ValueContainer>,
162 ) {
163 self.try_set(key, value)
164 .expect("Setting value in map failed");
165 }
166
167 pub(crate) fn try_set<'a>(
170 &mut self,
171 key: impl Into<ValueKey<'a>>,
172 value: impl Into<ValueContainer>,
173 ) -> Result<(), KeyNotFoundError> {
174 let key = key.into();
175 match self {
176 Map::Dynamic(map) => {
177 key.with_value_container(|key| {
178 map.insert(key.clone(), value.into());
179 });
180 Ok(())
181 }
182 Map::Fixed(vec) => key.with_value_container(|key| {
183 if let Some((_, v)) = vec.iter_mut().find(|(k, _)| k == key) {
184 *v = value.into();
185 Ok(())
186 } else {
187 Err(KeyNotFoundError { key: key.clone() })
188 }
189 }),
190 Map::Structural(vec) => {
191 if let Some(string) = key.try_as_text() {
192 if let Some((_, v)) =
193 vec.iter_mut().find(|(k, _)| k == string)
194 {
195 *v = value.into();
196 Ok(())
197 } else {
198 Err(KeyNotFoundError { key: key.into() })
199 }
200 } else {
201 Err(KeyNotFoundError { key: key.into() })
202 }
203 }
204 }
205 }
206}
207
208pub enum BorrowedMapKey<'a> {
209 Text(&'a str),
210 Value(&'a ValueContainer),
211}
212
213impl<'a> From<BorrowedMapKey<'a>> for ValueContainer {
214 fn from(key: BorrowedMapKey) -> Self {
215 match key {
216 BorrowedMapKey::Text(text) => {
217 ValueContainer::Value(Value::from(text))
218 }
219 BorrowedMapKey::Value(value) => value.clone(),
220 }
221 }
222}
223
224impl Hash for BorrowedMapKey<'_> {
225 fn hash<H: Hasher>(&self, state: &mut H) {
226 match self {
227 BorrowedMapKey::Text(text) => text.hash(state),
228 BorrowedMapKey::Value(value) => value.hash(state),
229 }
230 }
231}
232
233impl StructuralEq for BorrowedMapKey<'_> {
234 fn structural_eq(&self, other: &Self) -> bool {
235 match (self, other) {
236 (BorrowedMapKey::Text(a), BorrowedMapKey::Text(b)) => a == b,
237 (BorrowedMapKey::Value(a), BorrowedMapKey::Value(b)) => {
238 a.structural_eq(b)
239 }
240 (BorrowedMapKey::Text(a), BorrowedMapKey::Value(b))
241 | (BorrowedMapKey::Value(b), BorrowedMapKey::Text(a)) => {
242 if let ValueContainer::Value(Value {
243 inner: CoreValue::Text(text),
244 ..
245 }) = b
246 {
247 a == &text.0
248 } else {
249 false
250 }
251 }
252 }
253 }
254}
255
256impl Display for BorrowedMapKey<'_> {
257 fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
258 match self {
259 BorrowedMapKey::Text(string) => core::write!(f, "\"{}\"", string),
261 BorrowedMapKey::Value(value) => core::write!(f, "{value}"),
262 }
263 }
264}
265
266#[derive(Debug)]
267pub enum MapKey {
268 Text(String),
269 Value(ValueContainer),
270}
271
272impl From<MapKey> for ValueContainer {
273 fn from(key: MapKey) -> Self {
274 match key {
275 MapKey::Text(text) => ValueContainer::Value(Value::from(text)),
276 MapKey::Value(value) => value,
277 }
278 }
279}
280
281impl<'a> From<&'a MapKey> for ValueKey<'a> {
282 fn from(key: &'a MapKey) -> Self {
283 match key {
284 MapKey::Text(text) => ValueKey::Text(Cow::Borrowed(text)),
285 MapKey::Value(value) => ValueKey::Value(Cow::Borrowed(value)),
286 }
287 }
288}
289
290impl Display for MapKey {
291 fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
292 match self {
293 MapKey::Text(text) => core::write!(f, "{text}"),
294 MapKey::Value(value) => core::write!(f, "{value}"),
295 }
296 }
297}
298
299pub struct MapIterator<'a> {
300 map: &'a Map,
301 index: usize,
302}
303
304impl<'a> Iterator for MapIterator<'a> {
305 type Item = (BorrowedMapKey<'a>, &'a ValueContainer);
306
307 fn next(&mut self) -> Option<Self::Item> {
308 match self.map {
309 Map::Dynamic(map) => {
310 let item = map.iter().nth(self.index);
311 self.index += 1;
312 item.map(|(k, v)| {
313 let key = match k {
314 ValueContainer::Value(Value {
315 inner: CoreValue::Text(text),
316 ..
317 }) => BorrowedMapKey::Text(&text.0),
318 _ => BorrowedMapKey::Value(k),
319 };
320 (key, v)
321 })
322 }
323 Map::Fixed(vec) => {
324 if self.index < vec.len() {
325 let item = &vec[self.index];
326 self.index += 1;
327 let key = match &item.0 {
328 ValueContainer::Value(Value {
329 inner: CoreValue::Text(text),
330 ..
331 }) => BorrowedMapKey::Text(&text.0),
332 _ => BorrowedMapKey::Value(&item.0),
333 };
334 Some((key, &item.1))
335 } else {
336 None
337 }
338 }
339 Map::Structural(vec) => {
340 if self.index < vec.len() {
341 let item = &vec[self.index];
342 self.index += 1;
343 Some((BorrowedMapKey::Text(&item.0), &item.1))
344 } else {
345 None
346 }
347 }
348 }
349 }
350}
351
352pub enum MapMutIterator<'a> {
353 Dynamic(indexmap::map::IterMut<'a, ValueContainer, ValueContainer>),
354 Fixed(core::slice::IterMut<'a, (ValueContainer, ValueContainer)>),
355 Structural(core::slice::IterMut<'a, (String, ValueContainer)>),
356}
357
358impl<'a> Iterator for MapMutIterator<'a> {
359 type Item = (BorrowedMapKey<'a>, &'a mut ValueContainer);
360
361 fn next(&mut self) -> Option<Self::Item> {
362 match self {
363 MapMutIterator::Dynamic(iter) => iter.next().map(|(k, v)| {
364 let key = match k {
365 ValueContainer::Value(Value {
366 inner: CoreValue::Text(text),
367 ..
368 }) => BorrowedMapKey::Text(&text.0),
369 _ => BorrowedMapKey::Value(k),
370 };
371 (key, v)
372 }),
373 MapMutIterator::Fixed(iter) => iter.next().map(|(k, v)| {
374 let key = match k {
375 ValueContainer::Value(Value {
376 inner: CoreValue::Text(text),
377 ..
378 }) => BorrowedMapKey::Text(&text.0),
379 _ => BorrowedMapKey::Value(k),
380 };
381 (key, v)
382 }),
383 MapMutIterator::Structural(iter) => iter
384 .next()
385 .map(|(k, v)| (BorrowedMapKey::Text(k.as_str()), v)),
386 }
387 }
388}
389
390pub struct IntoMapIterator {
391 map: Map,
392 index: usize,
393}
394
395impl Iterator for IntoMapIterator {
396 type Item = (MapKey, ValueContainer);
397
398 fn next(&mut self) -> Option<Self::Item> {
399 match &self.map {
401 Map::Dynamic(map) => {
402 let item = map.iter().nth(self.index);
403 self.index += 1;
404 item.map(|(k, v)| {
405 let key = match k {
406 ValueContainer::Value(Value {
407 inner: CoreValue::Text(text),
408 ..
409 }) => MapKey::Text(text.0.clone()),
410 _ => MapKey::Value(k.clone()),
411 };
412 (key, v.clone())
413 })
414 }
415 Map::Fixed(vec) => {
416 if self.index < vec.len() {
417 let item = &vec[self.index];
418 self.index += 1;
419 let key = match &item.0 {
420 ValueContainer::Value(Value {
421 inner: CoreValue::Text(text),
422 ..
423 }) => MapKey::Text(text.0.clone()),
424 _ => MapKey::Value(item.0.clone()),
425 };
426 Some((key, item.1.clone()))
427 } else {
428 None
429 }
430 }
431 Map::Structural(vec) => {
432 if self.index < vec.len() {
433 let item = &vec[self.index];
434 self.index += 1;
435 Some((MapKey::Text(item.0.clone()), item.1.clone()))
436 } else {
437 None
438 }
439 }
440 }
441 }
442}
443
444impl StructuralEq for Map {
445 fn structural_eq(&self, other: &Self) -> bool {
446 if self.size() != other.size() {
447 return false;
448 }
449 for ((key, value), (other_key, other_value)) in
450 self.into_iter().zip(other.into_iter())
451 {
452 if !key.structural_eq(&other_key)
453 || !value.structural_eq(other_value)
454 {
455 return false;
456 }
457 }
458 true
459 }
460}
461
462impl Hash for Map {
463 fn hash<H: Hasher>(&self, state: &mut H) {
464 for (k, v) in self.into_iter() {
465 k.hash(state);
466 v.hash(state);
467 }
468 }
469}
470
471impl Display for Map {
472 fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
473 core::write!(f, "{{")?;
474 for (i, (key, value)) in self.into_iter().enumerate() {
475 if i > 0 {
476 core::write!(f, ", ")?;
477 }
478 core::write!(f, "{key}: {value}")?;
479 }
480 core::write!(f, "}}")
481 }
482}
483
484impl<K, V> From<HashMap<K, V>> for Map
485where
486 K: Into<ValueContainer>,
487 V: Into<ValueContainer>,
488{
489 fn from(map: HashMap<K, V>) -> Self {
490 Map::new(map.into_iter().map(|(k, v)| (k.into(), v.into())).collect())
491 }
492}
493
494impl IntoIterator for Map {
495 type Item = (MapKey, ValueContainer);
496 type IntoIter = IntoMapIterator;
497
498 fn into_iter(self) -> Self::IntoIter {
499 IntoMapIterator {
500 map: self,
501 index: 0,
502 }
503 }
504}
505
506impl<'a> IntoIterator for &'a Map {
507 type Item = (BorrowedMapKey<'a>, &'a ValueContainer);
508 type IntoIter = MapIterator<'a>;
509
510 fn into_iter(self) -> Self::IntoIter {
511 MapIterator {
512 map: self,
513 index: 0,
514 }
515 }
516}
517
518impl<'a> IntoIterator for &'a mut Map {
519 type Item = (BorrowedMapKey<'a>, &'a mut ValueContainer);
520 type IntoIter = MapMutIterator<'a>;
521
522 fn into_iter(self) -> Self::IntoIter {
523 match self {
524 Map::Dynamic(map) => MapMutIterator::Dynamic(map.iter_mut()),
525 Map::Fixed(vec) => MapMutIterator::Fixed(vec.iter_mut()),
526 Map::Structural(vec) => MapMutIterator::Structural(vec.iter_mut()),
527 }
528 }
529}
530
531impl From<Vec<(ValueContainer, ValueContainer)>> for Map {
532 fn from(vec: Vec<(ValueContainer, ValueContainer)>) -> Self {
534 Map::new(vec.into_iter().collect())
535 }
536}
537
538impl From<Vec<(String, ValueContainer)>> for Map {
539 fn from(vec: Vec<(String, ValueContainer)>) -> Self {
541 Map::new(
542 vec.into_iter()
543 .map(|(k, v)| (k.into(), v))
544 .collect::<IndexMap<ValueContainer, ValueContainer, RandomState>>(),
545 )
546 }
547}
548
549impl From<Vec<(MapKey, ValueContainer)>> for Map {
550 fn from(vec: Vec<(MapKey, ValueContainer)>) -> Self {
551 let has_only_text_keys = vec.iter().all(|(k, _)| {
552 matches!(k, MapKey::Text(_))
553 || matches!(
554 k,
555 MapKey::Value(ValueContainer::Value(Value {
556 inner: CoreValue::Text(_),
557 ..
558 }))
559 )
560 });
561 if has_only_text_keys {
562 let mut entries: Vec<(String, ValueContainer)> =
563 Vec::with_capacity(vec.len());
564 for (k, v) in vec {
565 match k {
566 MapKey::Text(text) => {
567 entries.push((text, v));
568 }
569 MapKey::Value(value) => {
570 if let ValueContainer::Value(Value {
571 inner: CoreValue::Text(text),
572 ..
573 }) = value
574 {
575 entries.push((text.0, v));
576 } else {
577 unreachable!(); }
579 }
580 }
581 }
582 Map::Structural(entries)
583 } else {
584 let mut map = Map::default();
585 for (k, v) in vec {
586 map.set(&k, v);
587 }
588 map
589 }
590 }
591}
592
593impl<K, V> FromIterator<(K, V)> for Map
594where
595 K: Into<ValueContainer>,
596 V: Into<ValueContainer>,
597{
598 fn from_iter<I: IntoIterator<Item = (K, V)>>(iter: I) -> Self {
599 Map::Dynamic(
600 iter.into_iter()
601 .map(|(k, v)| (k.into(), v.into()))
602 .collect(),
603 )
604 }
605}
606
607impl From<IndexMap<ValueContainer, ValueContainer, RandomState>> for Map {
608 fn from(
609 map: IndexMap<ValueContainer, ValueContainer, RandomState>,
610 ) -> Self {
611 Map::new(map)
612 }
613}
614impl From<IndexMap<String, ValueContainer, RandomState>> for Map {
615 fn from(map: IndexMap<String, ValueContainer, RandomState>) -> Self {
616 Map::new(
617 map.into_iter()
618 .map(|(k, v)| (k.into(), v))
619 .collect::<IndexMap<ValueContainer, ValueContainer, RandomState>>(),
620 )
621 }
622}
623
624impl TryFrom<CoreValue> for Map {
625 type Error = String;
626
627 fn try_from(value: CoreValue) -> Result<Self, Self::Error> {
628 if let CoreValue::Map(map) = value {
629 Ok(map)
630 } else {
631 Err(format!("Expected CoreValue::Map, found {value:?}"))
632 }
633 }
634}
635
636#[cfg(test)]
637mod tests {
638 use crate::values::core_values::decimal::Decimal;
639 use crate::values::core_values::decimal::typed_decimal::TypedDecimal;
640 use crate::values::core_values::map::Map;
641 use crate::values::value_container::ValueContainer;
642
643 #[test]
644 fn test_map() {
645 let mut map = Map::default();
646 map.set("key1", 42);
647 map.set("key2", "value2");
648 assert_eq!(map.size(), 2);
649 assert_eq!(map.get("key1").unwrap().to_string(), "42");
650 assert_eq!(map.get("key2").unwrap().to_string(), "\"value2\"");
651 assert_eq!(map.to_string(), r#"{"key1": 42, "key2": "value2"}"#);
652 }
653
654 #[test]
655 fn test_duplicate_keys() {
656 let mut map = Map::default();
657 map.set("key1", 42);
658 map.set("key1", "new_value");
659 assert_eq!(map.size(), 1);
660 assert_eq!(map.get("key1").unwrap().to_string(), "\"new_value\"");
661 }
662
663 #[test]
664 fn test_ref_keys() {
665 let mut map = Map::default();
666 let key = ValueContainer::new_reference(ValueContainer::from(42));
667 map.set(&key, "value");
668 assert_eq!(map.size(), 1);
670 assert!(map.has(&key));
671 assert_eq!(map.get(&key).unwrap().to_string(), "\"value\"");
672
673 let new_key = ValueContainer::new_reference(ValueContainer::from(42));
675 assert!(!map.has(&new_key));
676 assert!(map.get(&new_key).is_err());
677 }
678
679 #[test]
680 fn test_decimal_nan_value_key() {
681 let mut map = Map::default();
682 let nan_value = ValueContainer::from(Decimal::Nan);
683 map.set(&nan_value, "value");
684 assert_eq!(map.size(), 1);
686 assert!(map.has(&nan_value));
687
688 let new_nan_value = ValueContainer::from(Decimal::Nan);
690 assert!(map.has(&new_nan_value));
691
692 map.set(&new_nan_value, "new_value");
694 assert_eq!(map.size(), 1);
695 }
696
697 #[test]
698 fn test_float_nan_value_key() {
699 let mut map = Map::default();
700 let nan_value = ValueContainer::from(f64::NAN);
701 map.set(&nan_value, "value");
702 assert_eq!(map.size(), 1);
704 assert!(map.has(&nan_value));
705
706 let new_nan_value = ValueContainer::from(f64::NAN);
708 assert!(map.has(&new_nan_value));
709
710 let float32_nan_value = ValueContainer::from(f32::NAN);
712 assert!(!map.has(&float32_nan_value));
713
714 map.set(&new_nan_value, "new_value");
716 assert_eq!(map.size(), 1);
717 }
718
719 #[test]
720 fn test_decimal_zero_value_key() {
721 let mut map = Map::default();
722 let zero_value = ValueContainer::from(Decimal::Zero);
723 map.set(&zero_value, "value");
724 assert_eq!(map.size(), 1);
726 assert!(map.has(&zero_value));
727
728 let new_zero_value = ValueContainer::from(Decimal::Zero);
730 println!("new_zero_value: {:?}", new_zero_value);
731 assert!(map.has(&new_zero_value));
732
733 let neg_zero_value = ValueContainer::from(Decimal::NegZero);
735 assert!(map.has(&neg_zero_value));
736
737 map.set(&neg_zero_value, "new_value");
739 assert_eq!(map.size(), 1);
740 }
741
742 #[test]
743 fn test_float_zero_value_key() {
744 let mut map = Map::default();
745 let zero_value = ValueContainer::from(0.0f64);
746 map.set(&zero_value, "value");
747 assert_eq!(map.size(), 1);
749 assert!(map.has(&zero_value));
750 let new_zero_value = ValueContainer::from(0.0f64);
752 assert!(map.has(&new_zero_value));
753 let neg_zero_value = ValueContainer::from(-0.0f64);
755 assert!(map.has(&neg_zero_value));
756
757 map.set(&neg_zero_value, "new_value");
759 assert_eq!(map.size(), 1);
760
761 let float32_zero_value = ValueContainer::from(0.0f32);
763 assert!(!map.has(&float32_zero_value));
764 }
765
766 #[test]
767 fn test_typed_big_decimal_key() {
768 let mut map = Map::default();
769 let zero_big_decimal =
770 ValueContainer::from(TypedDecimal::Decimal(Decimal::Zero));
771 map.set(&zero_big_decimal, "value");
772 assert_eq!(map.size(), 1);
774 assert!(map.has(&zero_big_decimal));
775 let new_zero_big_decimal =
777 ValueContainer::from(TypedDecimal::Decimal(Decimal::Zero));
778 assert!(map.has(&new_zero_big_decimal));
779 let neg_zero_big_decimal =
781 ValueContainer::from(TypedDecimal::Decimal(Decimal::NegZero));
782 assert!(map.has(&neg_zero_big_decimal));
783
784 map.set(&neg_zero_big_decimal, "new_value");
786 assert_eq!(map.size(), 1);
787 }
788}