1#[fp_macros::document_module]
6mod inner {
7 use {
8 crate::{
9 Apply,
10 brands::optics::*,
11 classes::{
12 profunctor::{
13 Choice,
14 Profunctor,
15 Strong,
16 },
17 *,
18 },
19 impl_kind,
20 kinds::*,
21 },
22 fp_macros::*,
23 };
24
25 #[document_type_parameters(
27 "The lifetime of the functions.",
28 "The cloneable function brand.",
29 "The type of the value produced by the preview function.",
30 "The type of the value consumed by the setter.",
31 "The source type of the structure.",
32 "The target type of the structure."
33 )]
34 pub struct Stall<'a, FunctionBrand: LiftFn, A: 'a, B: 'a, S: 'a, T: 'a> {
35 pub get: <FunctionBrand as CloneFn>::Of<'a, S, Result<A, T>>,
37 pub set: <FunctionBrand as CloneFn>::Of<'a, (S, B), T>,
39 }
40
41 #[document_type_parameters(
42 "The lifetime of the functions.",
43 "The cloneable function brand.",
44 "The type of the value produced by the preview function.",
45 "The type of the value consumed by the setter.",
46 "The source type of the structure.",
47 "The target type of the structure."
48 )]
49 impl<'a, FunctionBrand: LiftFn, A: 'a, B: 'a, S: 'a, T: 'a> Stall<'a, FunctionBrand, A, B, S, T> {
50 #[document_signature]
52 #[document_parameters("The preview function.", "The setter function.")]
54 #[document_returns("A new instance of the type.")]
56 #[document_examples]
58 pub fn new(
74 get: <FunctionBrand as CloneFn>::Of<'a, S, Result<A, T>>,
75 set: <FunctionBrand as CloneFn>::Of<'a, (S, B), T>,
76 ) -> Self {
77 Stall {
78 get,
79 set,
80 }
81 }
82 }
83
84 impl_kind! {
85 impl<FunctionBrand: LiftFn + 'static, A: 'static, B: 'static> for StallBrand<FunctionBrand, A, B> {
86 #[document_default]
87 type Of<'a, S: 'a, T: 'a>: 'a = Stall<'a, FunctionBrand, A, B, S, T>;
88 }
89 }
90
91 #[document_type_parameters(
92 "The cloneable function brand.",
93 "The type of the value produced by the preview function.",
94 "The type of the value consumed by the setter."
95 )]
96 impl<FunctionBrand: LiftFn + 'static, A: 'static, B: 'static> Profunctor
97 for StallBrand<FunctionBrand, A, B>
98 {
99 #[document_signature]
101 #[document_type_parameters(
102 "The lifetime of the functions.",
103 "The source type of the new structure.",
104 "The target type of the new structure.",
105 "The source type of the original structure.",
106 "The target type of the original structure."
107 )]
108 #[document_parameters(
110 "The function to apply to the input.",
111 "The function to apply to the output.",
112 "The stall instance to transform."
113 )]
114 #[document_returns("A transformed `Stall` instance.")]
115 #[document_examples]
117 fn dimap<'a, S: 'a, T: 'a, U: 'a, V: 'a>(
145 st: impl Fn(S) -> T + 'a,
146 uv: impl Fn(U) -> V + 'a,
147 puv: Apply!(<Self as Kind!( type Of<'a, T: 'a, U: 'a>: 'a; )>::Of<'a, T, U>),
148 ) -> Apply!(<Self as Kind!( type Of<'a, T: 'a, U: 'a>: 'a; )>::Of<'a, S, V>) {
149 let get = puv.get;
150 let set = puv.set;
151 let st = <FunctionBrand as LiftFn>::new(st);
152 let uv = <FunctionBrand as LiftFn>::new(uv);
153 let st_2 = st.clone();
154 let uv_2 = uv.clone();
155 Stall::new(
156 <FunctionBrand as LiftFn>::new(move |s: S| (*get)((*st)(s)).map_err(|u| (*uv)(u))),
157 <FunctionBrand as LiftFn>::new(move |(s, b): (S, B)| {
158 (*uv_2)((*set)(((*st_2)(s), b)))
159 }),
160 )
161 }
162 }
163
164 #[document_type_parameters(
165 "The cloneable function brand.",
166 "The type of the value produced by the preview function.",
167 "The type of the value consumed by the setter."
168 )]
169 impl<FunctionBrand: LiftFn + 'static, A: 'static, B: 'static> Strong
170 for StallBrand<FunctionBrand, A, B>
171 {
172 #[document_signature]
174 #[document_type_parameters(
175 "The lifetime of the functions.",
176 "The source type of the structure.",
177 "The target type of the structure.",
178 "The type of the other component."
179 )]
180 #[document_parameters("The stall instance to transform.")]
182 #[document_returns("A transformed `Stall` instance that operates on tuples.")]
183 #[document_examples]
185 fn first<'a, S: 'a, T: 'a, C: 'a>(
208 pab: Apply!(<Self as Kind!( type Of<'a, T: 'a, U: 'a>: 'a; )>::Of<'a, S, T>)
209 ) -> Apply!(<Self as Kind!( type Of<'a, T: 'a, U: 'a>: 'a; )>::Of<'a, (S, C), (T, C)>) {
210 let get = pab.get;
211 let set = pab.set;
212 Stall::new(
213 <FunctionBrand as LiftFn>::new(move |(s, c): (S, C)| (*get)(s).map_err(|t| (t, c))),
214 <FunctionBrand as LiftFn>::new(move |((s, c), b): ((S, C), B)| ((*set)((s, b)), c)),
215 )
216 }
217 }
218
219 #[document_type_parameters(
220 "The cloneable function brand.",
221 "The type of the value produced by the preview function.",
222 "The type of the value consumed by the setter."
223 )]
224 impl<FunctionBrand: LiftFn + 'static, A: 'static, B: 'static> Choice
225 for StallBrand<FunctionBrand, A, B>
226 {
227 #[document_signature]
229 #[document_type_parameters(
230 "The lifetime of the functions.",
231 "The source type of the structure.",
232 "The target type of the structure.",
233 "The type of the other component."
234 )]
235 #[document_parameters("The stall instance to transform.")]
237 #[document_returns(
238 "A transformed `Stall` instance that operates on the left component of a `Result`."
239 )]
240 #[document_examples]
242 fn left<'a, S: 'a, T: 'a, C: 'a>(
265 pab: Apply!(<Self as Kind!( type Of<'a, T: 'a, U: 'a>: 'a; )>::Of<'a, S, T>)
266 ) -> Apply!(<Self as Kind!( type Of<'a, T: 'a, U: 'a>: 'a; )>::Of<'a, Result<C, S>, Result<C, T>>)
267 {
268 let get = pab.get;
269 let set = pab.set;
270 Stall::new(
271 <FunctionBrand as LiftFn>::new(move |r: Result<C, S>| match r {
272 Err(s) => (*get)(s).map_err(Err),
273 Ok(c) => Err(Ok(c)),
274 }),
275 <FunctionBrand as LiftFn>::new(move |(r, b): (Result<C, S>, B)| match r {
276 Err(s) => Err((*set)((s, b))),
277 Ok(c) => Ok(c),
278 }),
279 )
280 }
281
282 #[document_signature]
284 #[document_type_parameters(
285 "The lifetime of the functions.",
286 "The source type of the structure.",
287 "The target type of the structure.",
288 "The type of the other component."
289 )]
290 #[document_parameters("The stall instance to transform.")]
292 #[document_returns(
293 "A transformed `Stall` instance that operates on the right component of a `Result`."
294 )]
295 #[document_examples]
297 fn right<'a, S: 'a, T: 'a, C: 'a>(
320 pab: Apply!(<Self as Kind!( type Of<'a, T: 'a, U: 'a>: 'a; )>::Of<'a, S, T>)
321 ) -> Apply!(<Self as Kind!( type Of<'a, T: 'a, U: 'a>: 'a; )>::Of<'a, Result<S, C>, Result<T, C>>)
322 {
323 let get = pab.get;
324 let set = pab.set;
325 Stall::new(
326 <FunctionBrand as LiftFn>::new(move |r: Result<S, C>| match r {
327 Ok(s) => (*get)(s).map_err(Ok),
328 Err(c) => Err(Err(c)),
329 }),
330 <FunctionBrand as LiftFn>::new(move |(r, b): (Result<S, C>, B)| match r {
331 Ok(s) => Ok((*set)((s, b))),
332 Err(c) => Err(c),
333 }),
334 )
335 }
336 }
337}
338pub use inner::*;