arc_string_interner/
serde_impl.rs

1use super::*;
2
3use std::default::Default;
4
5use std::fmt;
6
7use serde::de::{Deserialize, Deserializer, SeqAccess, Visitor};
8use serde::ser::{Serialize, SerializeSeq, Serializer};
9
10impl<Sym, H> Serialize for StringInterner<Sym, H>
11where
12    Sym: Symbol,
13    H: BuildHasher,
14{
15    fn serialize<S>(&self, serializer: S) -> Result<S::Ok, S::Error>
16    where
17        S: Serializer,
18    {
19        let mut seq = serializer.serialize_seq(Some(self.len()))?;
20        for s in self.iter_values() {
21            seq.serialize_element(s.as_ref())?
22        }
23        seq.end()
24    }
25}
26
27impl<'de, Sym, H> Deserialize<'de> for StringInterner<Sym, H>
28where
29    Sym: Symbol,
30    H: BuildHasher + Default,
31{
32    fn deserialize<D>(deserializer: D) -> Result<StringInterner<Sym, H>, D::Error>
33    where
34        D: Deserializer<'de>,
35    {
36        deserializer.deserialize_seq(StringInternerVisitor::default())
37    }
38}
39
40struct StringInternerVisitor<Sym, H>
41where
42    Sym: Symbol,
43    H: BuildHasher,
44{
45    mark: marker::PhantomData<(Sym, H)>,
46}
47
48impl<Sym, H> Default for StringInternerVisitor<Sym, H>
49where
50    Sym: Symbol,
51    H: BuildHasher,
52{
53    fn default() -> Self {
54        StringInternerVisitor {
55            mark: marker::PhantomData,
56        }
57    }
58}
59
60impl<'de, Sym, H> Visitor<'de> for StringInternerVisitor<Sym, H>
61where
62    Sym: Symbol,
63    H: BuildHasher + Default,
64{
65    type Value = StringInterner<Sym, H>;
66
67    fn expecting(&self, formatter: &mut fmt::Formatter) -> fmt::Result {
68        formatter.write_str("Expected a contiguous sequence of strings.")
69    }
70
71    fn visit_seq<A>(self, mut seq: A) -> Result<Self::Value, A::Error>
72    where
73        A: SeqAccess<'de>,
74    {
75        let mut interner: StringInterner<Sym, H> =
76            StringInterner::with_capacity_and_hasher(seq.size_hint().unwrap_or(0), H::default());
77        while let Some(s) = seq.next_element::<Box<str>>()? {
78            interner.get_or_intern(s);
79        }
80        Ok(interner)
81    }
82}