1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
use std::{collections::HashMap, error::Error, hash::Hash};

use super::*;

impl<KI, VI, KF, VF> ExtraInto<HashMap<KI, VI>> for HashMap<KF, VF>
where
    KI: Eq + Hash,
    KF: Into<KI> + Eq + Hash,
    VF: Into<VI>,
{
    fn into_extra(self) -> HashMap<KI, VI> {
        self.into_iter().map(|(k, v)| (k.into(), v.into())).collect()
    }
}

/// Mapper for [HashMap]
pub fn hashmap<KI, VI, KF, VF>(from: HashMap<KF, VF>) -> HashMap<KI, VI>
where
    KI: Eq + Hash,
    KF: Eq + Hash,
    KF: Into<KI>,
    VF: Into<VI>,
{
    from.into_iter().map(|(k, v)| (k.into(), v.into())).collect()
}

/// Mapper for [HashMap]
pub fn hashmap_extra<KI, VI, KF, VF>(from: HashMap<KF, VF>) -> HashMap<KI, VI>
where
    KI: Eq + Hash,
    KF: Eq + Hash,
    KF: ExtraInto<KI>,
    VF: ExtraInto<VI>,
{
    from.into_iter()
        .map(|(k, v)| (k.into_extra(), v.into_extra()))
        .collect()
}

impl<KI, VI, KF, VF> TryExtraInto<HashMap<KI, VI>> for HashMap<KF, VF>
where
    KI: Eq + Hash,
    KF: TryInto<KI> + Eq + Hash,
    <KF as TryInto<KI>>::Error: Error + Send + Sync + 'static,
    VF: TryInto<VI>,
    <VF as TryInto<VI>>::Error: Error + Send + Sync + 'static,
{
    type Error = anyhow::Error;

    fn try_into_extra(self) -> Result<HashMap<KI, VI>, Self::Error> {
        let mut ret = HashMap::with_capacity(self.len());
        for (k, v) in self.into_iter().map(|(k, v)| (k.try_into(), v.try_into())) {
            ret.insert(k?, v?);
        }
        Ok(ret)
    }
}

/// Mapper for [HashMap]
pub fn try_hashmap<KI, VI, KF, VF>(from: HashMap<KF, VF>) -> Result<HashMap<KI, VI>, anyhow::Error>
where
    KI: Eq + Hash,
    KF: Eq + Hash,
    KF: TryInto<KI>,
    <KF as TryInto<KI>>::Error: Error + Send + Sync + 'static,
    VF: TryInto<VI>,
    <VF as TryInto<VI>>::Error: Error + Send + Sync + 'static,
{
    let mut ret = HashMap::with_capacity(from.len());
    for (k, v) in from.into_iter().map(|(k, v)| (k.try_into(), v.try_into())) {
        ret.insert(k?, v?);
    }
    Ok(ret)
}

/// Mapper for [HashMap]
pub fn try_hashmap_extra<KI, VI, KF, VF>(from: HashMap<KF, VF>) -> Result<HashMap<KI, VI>, anyhow::Error>
where
    KI: Eq + Hash,
    KF: Eq + Hash,
    KF: TryExtraInto<KI>,
    <KF as TryExtraInto<KI>>::Error: Error + Send + Sync + 'static,
    VF: TryExtraInto<VI>,
    <VF as TryExtraInto<VI>>::Error: Error + Send + Sync + 'static,
{
    let mut ret = HashMap::with_capacity(from.len());
    for (k, v) in from.into_iter().map(|(k, v)| (k.try_into_extra(), v.try_into_extra())) {
        ret.insert(k?, v?);
    }
    Ok(ret)
}