1use std::collections::{BTreeMap, BTreeSet, BinaryHeap, HashMap, HashSet, LinkedList, VecDeque};
2use std::hash::{BuildHasher, Hash};
3
4use higher::Lift;
5
6pub trait Functor<A, B>: Lift<A, B> {
16 fn map<F>(self, f: F) -> <Self as Lift<A, B>>::Target1
17 where
18 F: Fn(A) -> B;
19}
20
21impl<A, B> Functor<A, B> for Option<A> {
22 fn map<F>(self, f: F) -> <Self as Lift<A, B>>::Target1
23 where
24 F: Fn(A) -> B,
25 {
26 self.map(f)
27 }
28}
29
30impl<A, B, E> Functor<A, B> for Result<A, E> {
31 fn map<F>(self, f: F) -> <Self as Lift<A, B>>::Target1
32 where
33 F: Fn(A) -> B,
34 {
35 self.map(f)
36 }
37}
38
39impl<A, B> Functor<A, B> for Vec<A> {
40 fn map<F>(self, f: F) -> <Self as Lift<A, B>>::Target1
41 where
42 F: Fn(A) -> B,
43 {
44 self.into_iter().map(f).collect()
45 }
46}
47
48impl<A, B, S> Functor<A, B> for HashSet<A, S>
49where
50 A: Hash + Eq,
51 B: Hash + Eq,
52 S: BuildHasher + Default,
53{
54 fn map<F>(self, f: F) -> <Self as Lift<A, B>>::Target1
55 where
56 F: Fn(A) -> B,
57 {
58 self.into_iter().map(f).collect()
59 }
60}
61
62impl<A, B> Functor<A, B> for BTreeSet<A>
63where
64 A: Ord,
65 B: Ord,
66{
67 fn map<F>(self, f: F) -> <Self as Lift<A, B>>::Target1
68 where
69 F: Fn(A) -> B,
70 {
71 self.into_iter().map(f).collect()
72 }
73}
74
75impl<A, B, C, D, S> Functor<(A, B), (C, D)> for HashMap<A, B, S>
76where
77 A: Hash + Eq,
78 B: Hash + Eq,
79 C: Hash + Eq,
80 D: Hash + Eq,
81 S: BuildHasher + Default,
82{
83 fn map<F>(self, f: F) -> <Self as Lift<(A, B), (C, D)>>::Target1
84 where
85 F: Fn((A, B)) -> (C, D),
86 {
87 self.into_iter().map(f).collect()
88 }
89}
90
91impl<A, B, C, D> Functor<(A, B), (C, D)> for BTreeMap<A, B>
92where
93 A: Ord,
94 B: Ord,
95 C: Ord,
96 D: Ord,
97{
98 fn map<F>(self, f: F) -> <Self as Lift<(A, B), (C, D)>>::Target1
99 where
100 F: Fn((A, B)) -> (C, D),
101 {
102 self.into_iter().map(f).collect()
103 }
104}
105
106impl<A, B> Functor<A, B> for VecDeque<A> {
107 fn map<F>(self, f: F) -> <Self as Lift<A, B>>::Target1
108 where
109 F: Fn(A) -> B,
110 {
111 self.into_iter().map(f).collect()
112 }
113}
114
115impl<A, B> Functor<A, B> for LinkedList<A> {
116 fn map<F>(self, f: F) -> <Self as Lift<A, B>>::Target1
117 where
118 F: Fn(A) -> B,
119 {
120 self.into_iter().map(f).collect()
121 }
122}
123
124impl<A, B> Functor<A, B> for BinaryHeap<A>
125where
126 A: Ord,
127 B: Ord,
128{
129 fn map<F>(self, f: F) -> <Self as Lift<A, B>>::Target1
130 where
131 F: Fn(A) -> B,
132 {
133 self.into_iter().map(f).collect()
134 }
135}