1#[fp_macros::document_module]
39pub(crate) mod inner {
40 use {
41 crate::{
42 classes::{
43 RefSemimonad,
44 Semimonad,
45 },
46 dispatch::{
47 Ref,
48 Val,
49 },
50 kinds::*,
51 },
52 fp_macros::*,
53 };
54
55 #[document_type_parameters(
63 "The lifetime of the values.",
64 "The brand of the monad.",
65 "The type of the value inside the monad.",
66 "The type of the result.",
67 "The container type (owned or borrowed), inferred from the argument.",
68 "Dispatch marker type, inferred automatically."
69 )]
70 #[document_parameters("The closure implementing this dispatch.")]
71 pub trait BindDispatch<'a, Brand: Kind_cdc7cd43dac7585f, A: 'a, B: 'a, FA, Marker> {
72 #[document_signature]
74 #[document_parameters("The monadic value.")]
75 #[document_returns("The result of binding.")]
76 #[document_examples]
77 fn dispatch(
87 self,
88 ma: FA,
89 ) -> Apply!(<Brand as Kind!( type Of<'a, T: 'a>: 'a; )>::Of<'a, B>);
90 }
91
92 #[document_type_parameters(
94 "The lifetime.",
95 "The brand.",
96 "The input type.",
97 "The output type.",
98 "The closure type."
99 )]
100 #[document_parameters("The closure that takes owned values.")]
101 impl<'a, Brand, A, B, F>
102 BindDispatch<
103 'a,
104 Brand,
105 A,
106 B,
107 Apply!(<Brand as Kind!( type Of<'a, T: 'a>: 'a; )>::Of<'a, A>),
108 Val,
109 > for F
110 where
111 Brand: Semimonad,
112 A: 'a,
113 B: 'a,
114 F: Fn(A) -> Apply!(<Brand as Kind!( type Of<'a, T: 'a>: 'a; )>::Of<'a, B>) + 'a,
115 {
116 #[document_signature]
117 #[document_parameters("The monadic value.")]
118 #[document_returns("The result of binding.")]
119 #[document_examples]
120 fn dispatch(
130 self,
131 ma: Apply!(<Brand as Kind!( type Of<'a, T: 'a>: 'a; )>::Of<'a, A>),
132 ) -> Apply!(<Brand as Kind!( type Of<'a, T: 'a>: 'a; )>::Of<'a, B>) {
133 Brand::bind(ma, self)
134 }
135 }
136
137 #[document_type_parameters(
141 "The lifetime.",
142 "The borrow lifetime.",
143 "The brand.",
144 "The input type.",
145 "The output type.",
146 "The closure type."
147 )]
148 #[document_parameters("The closure that takes references.")]
149 impl<'a, 'b, Brand, A, B, F>
150 BindDispatch<
151 'a,
152 Brand,
153 A,
154 B,
155 &'b Apply!(<Brand as Kind!( type Of<'a, T: 'a>: 'a; )>::Of<'a, A>),
156 Ref,
157 > for F
158 where
159 Brand: RefSemimonad,
160 A: 'a,
161 B: 'a,
162 F: Fn(&A) -> Apply!(<Brand as Kind!( type Of<'a, T: 'a>: 'a; )>::Of<'a, B>) + 'a,
163 {
164 #[document_signature]
165 #[document_parameters("A reference to the monadic value.")]
166 #[document_returns("The result of binding.")]
167 #[document_examples]
168 fn dispatch(
185 self,
186 ma: &'b Apply!(<Brand as Kind!( type Of<'a, T: 'a>: 'a; )>::Of<'a, A>),
187 ) -> Apply!(<Brand as Kind!( type Of<'a, T: 'a>: 'a; )>::Of<'a, B>) {
188 Brand::ref_bind(ma, self)
189 }
190 }
191
192 #[document_type_parameters(
199 "The lifetime of the values.",
200 "The higher-kinded type brand.",
201 "The input type.",
202 "The intermediate type.",
203 "The output type.",
204 "Marker type (`Val` or `Ref`), inferred from the closures."
205 )]
206 #[document_parameters("The closure pair implementing this dispatch.")]
207 pub trait ComposeKleisliDispatch<'a, Brand: Kind_cdc7cd43dac7585f, A: 'a, B: 'a, C: 'a, Marker>
208 {
209 #[document_signature]
211 #[document_parameters("The input value.")]
212 #[document_returns("The result of composing f then g applied to the input.")]
213 #[document_examples]
214 fn dispatch(
225 self,
226 a: A,
227 ) -> Apply!(<Brand as Kind!( type Of<'a, T: 'a>: 'a; )>::Of<'a, C>);
228 }
229
230 #[document_type_parameters(
231 "The lifetime of the values.",
232 "The higher-kinded type brand.",
233 "The input type.",
234 "The intermediate type.",
235 "The output type.",
236 "The first closure type.",
237 "The second closure type."
238 )]
239 #[document_parameters("The closure pair.")]
240 impl<'a, Brand, A, B, C, F, G> ComposeKleisliDispatch<'a, Brand, A, B, C, Val> for (F, G)
241 where
242 Brand: Semimonad,
243 A: 'a,
244 B: 'a,
245 C: 'a,
246 F: Fn(A) -> Apply!(<Brand as Kind!( type Of<'a, T: 'a>: 'a; )>::Of<'a, B>) + 'a,
247 G: Fn(B) -> Apply!(<Brand as Kind!( type Of<'a, T: 'a>: 'a; )>::Of<'a, C>) + 'a,
248 {
249 #[document_signature]
250 #[document_parameters("The input value.")]
251 #[document_returns("The composed result.")]
252 #[document_examples]
253 fn dispatch(
264 self,
265 a: A,
266 ) -> Apply!(<Brand as Kind!( type Of<'a, T: 'a>: 'a; )>::Of<'a, C>) {
267 Brand::bind(self.0(a), self.1)
268 }
269 }
270
271 #[document_type_parameters(
272 "The lifetime of the values.",
273 "The higher-kinded type brand.",
274 "The input type.",
275 "The intermediate type.",
276 "The output type.",
277 "The first closure type.",
278 "The second closure type."
279 )]
280 #[document_parameters("The closure pair.")]
281 impl<'a, Brand, A, B, C, F, G> ComposeKleisliDispatch<'a, Brand, A, B, C, Ref> for (F, G)
282 where
283 Brand: RefSemimonad,
284 A: 'a,
285 B: 'a,
286 C: 'a,
287 F: Fn(&A) -> Apply!(<Brand as Kind!( type Of<'a, T: 'a>: 'a; )>::Of<'a, B>) + 'a,
288 G: Fn(&B) -> Apply!(<Brand as Kind!( type Of<'a, T: 'a>: 'a; )>::Of<'a, C>) + 'a,
289 {
290 #[document_signature]
291 #[document_parameters("The input value.")]
292 #[document_returns("The composed result.")]
293 #[document_examples]
294 fn dispatch(
317 self,
318 a: A,
319 ) -> Apply!(<Brand as Kind!( type Of<'a, T: 'a>: 'a; )>::Of<'a, C>) {
320 Brand::ref_bind(&(self.0(&a)), self.1)
321 }
322 }
323
324 #[document_signature]
329 #[document_type_parameters(
331 "The lifetime of the values.",
332 "The higher-kinded type brand.",
333 "The input type.",
334 "The intermediate type.",
335 "The output type.",
336 "Marker type, inferred from the closures."
337 )]
338 #[document_parameters("A tuple of (first arrow, second arrow).", "The input value.")]
340 #[document_returns("The result of applying f then g.")]
342 #[document_examples]
343 pub fn compose_kleisli<'a, Brand: Kind_cdc7cd43dac7585f, A: 'a, B: 'a, C: 'a, Marker>(
355 fg: impl ComposeKleisliDispatch<'a, Brand, A, B, C, Marker>,
356 a: A,
357 ) -> Apply!(<Brand as Kind!( type Of<'a, T: 'a>: 'a; )>::Of<'a, C>) {
358 fg.dispatch(a)
359 }
360
361 #[document_signature]
368 #[document_type_parameters(
370 "The lifetime of the values.",
371 "The higher-kinded type brand.",
372 "The input type.",
373 "The intermediate type.",
374 "The output type.",
375 "The second arrow type (`B -> Of<C>`).",
376 "The first arrow type (`A -> Of<B>`).",
377 "Marker type, inferred from the closures."
378 )]
379 #[document_parameters("A tuple of (second arrow, first arrow).", "The input value.")]
381 #[document_returns("The result of applying g then f.")]
383 #[document_examples]
384 pub fn compose_kleisli_flipped<
398 'a,
399 Brand: Kind_cdc7cd43dac7585f,
400 A: 'a,
401 B: 'a,
402 C: 'a,
403 F,
404 G,
405 Marker,
406 >(
407 gf: (F, G),
408 a: A,
409 ) -> Apply!(<Brand as Kind!( type Of<'a, T: 'a>: 'a; )>::Of<'a, C>)
410 where
411 (G, F): ComposeKleisliDispatch<'a, Brand, A, B, C, Marker>, {
412 ComposeKleisliDispatch::dispatch((gf.1, gf.0), a)
413 }
414
415 #[document_type_parameters(
423 "The lifetime of the values.",
424 "The brand of the monad.",
425 "The type of the value(s) inside the inner layer.",
426 "Dispatch marker type, inferred automatically. Either [`Val`](crate::dispatch::Val) or [`Ref`](crate::dispatch::Ref)."
427 )]
428 #[document_parameters("The container implementing this dispatch.")]
429 pub trait JoinDispatch<'a, Brand: Kind_cdc7cd43dac7585f, A: 'a, Marker> {
430 #[document_signature]
432 #[document_returns("A container with one layer of nesting removed.")]
434 #[document_examples]
435 fn dispatch(self) -> Apply!(<Brand as Kind!( type Of<'a, T: 'a>: 'a; )>::Of<'a, A>);
446 }
447
448 #[document_type_parameters("The lifetime.", "The brand.", "The inner element type.")]
452 #[document_parameters("The nested monadic value.")]
453 impl<'a, Brand, A> JoinDispatch<'a, Brand, A, Val> for Apply!(<Brand as Kind!( type Of<'a, T: 'a>: 'a; )>::Of<'a, Apply!(<Brand as Kind!( type Of<'a, T: 'a>: 'a; )>::Of<'a, A>)>)
454 where
455 Brand: Semimonad,
456 A: 'a,
457 {
458 #[document_signature]
459 #[document_returns("A container with one layer of nesting removed.")]
461 #[document_examples]
462 fn dispatch(self) -> Apply!(<Brand as Kind!( type Of<'a, T: 'a>: 'a; )>::Of<'a, A>) {
473 Brand::bind(self, |ma| ma)
474 }
475 }
476
477 #[document_type_parameters("The lifetime.", "The brand.", "The inner element type.")]
481 #[document_parameters("A reference to the nested monadic value.")]
482 impl<'a, Brand, A> JoinDispatch<'a, Brand, A, Ref> for &Apply!(<Brand as Kind!( type Of<'a, T: 'a>: 'a; )>::Of<'a, Apply!(<Brand as Kind!( type Of<'a, T: 'a>: 'a; )>::Of<'a, A>)>)
483 where
484 Brand: RefSemimonad,
485 A: 'a,
486 Apply!(<Brand as Kind!( type Of<'a, T: 'a>: 'a; )>::Of<'a, A>): Clone,
487 {
488 #[document_signature]
489 #[document_returns("A container with one layer of nesting removed.")]
491 #[document_examples]
492 fn dispatch(self) -> Apply!(<Brand as Kind!( type Of<'a, T: 'a>: 'a; )>::Of<'a, A>) {
504 Brand::ref_bind(self, |ma| ma.clone())
505 }
506 }
507
508 #[document_signature]
518 #[document_type_parameters(
520 "The lifetime of the values.",
521 "The container type (owned or borrowed). Brand is inferred from this.",
522 "The type of the value inside the monad.",
523 "The type of the result.",
524 "Dispatch marker type, inferred automatically."
525 )]
526 #[document_parameters(
528 "The monadic value (owned for Val, borrowed for Ref).",
529 "The function to apply to the value."
530 )]
531 #[document_returns("The result of sequencing the computation.")]
533 #[document_examples]
534 pub fn bind<'a, FA, A: 'a, B: 'a, Marker>(
542 ma: FA,
543 f: impl BindDispatch<'a, <FA as InferableBrand_cdc7cd43dac7585f>::Brand, A, B, FA, Marker>,
544 ) -> Apply!(<<FA as InferableBrand!(type Of<'a, A: 'a>: 'a;)>::Brand as Kind!( type Of<'a, T: 'a>: 'a; )>::Of<'a, B>)
545 where
546 FA: InferableBrand_cdc7cd43dac7585f, {
547 f.dispatch(ma)
548 }
549
550 #[document_signature]
559 #[document_type_parameters(
561 "The lifetime of the values.",
562 "The container type (owned or borrowed). Brand is inferred from this.",
563 "The input element type.",
564 "The output element type.",
565 "Dispatch marker type, inferred automatically."
566 )]
567 #[document_parameters(
569 "The function to apply to each element.",
570 "The monadic value (owned for Val, borrowed for Ref)."
571 )]
572 #[document_returns("The result of binding the function over the value.")]
574 #[document_examples]
575 pub fn bind_flipped<'a, FA, A: 'a, B: 'a, Marker>(
583 f: impl BindDispatch<'a, <FA as InferableBrand_cdc7cd43dac7585f>::Brand, A, B, FA, Marker>,
584 ma: FA,
585 ) -> Apply!(<<FA as InferableBrand!(type Of<'a, A: 'a>: 'a;)>::Brand as Kind!( type Of<'a, T: 'a>: 'a; )>::Of<'a, B>)
586 where
587 FA: InferableBrand_cdc7cd43dac7585f, {
588 f.dispatch(ma)
589 }
590
591 #[document_signature]
599 #[document_type_parameters(
601 "The lifetime of the values.",
602 "The container type (owned or borrowed). Brand is inferred from this.",
603 "The type of the value(s) inside the inner layer.",
604 "Dispatch marker type, inferred automatically."
605 )]
606 #[document_parameters("The nested monadic value (owned or borrowed).")]
608 #[document_returns("A container with one layer of nesting removed.")]
610 #[document_examples]
611 pub fn join<'a, FA, A: 'a, Marker>(
621 mma: FA
622 ) -> <<FA as InferableBrand_cdc7cd43dac7585f>::Brand as Kind_cdc7cd43dac7585f>::Of<'a, A>
623 where
624 FA: InferableBrand_cdc7cd43dac7585f
625 + JoinDispatch<'a, <FA as InferableBrand_cdc7cd43dac7585f>::Brand, A, Marker>, {
626 mma.dispatch()
627 }
628
629 pub mod explicit {
636 use super::*;
637
638 #[document_signature]
648 #[document_type_parameters(
650 "The lifetime of the values.",
651 "The brand of the monad.",
652 "The type of the value inside the monad.",
653 "The type of the result.",
654 "The container type (owned or borrowed), inferred from the argument.",
655 "Dispatch marker type, inferred automatically."
656 )]
657 #[document_parameters(
659 "The monadic value (owned for Val, borrowed for Ref).",
660 "The function to apply to the value."
661 )]
662 #[document_returns("The result of sequencing the computation.")]
664 #[document_examples]
665 pub fn bind<'a, Brand: Kind_cdc7cd43dac7585f, A: 'a, B: 'a, FA, Marker>(
675 ma: FA,
676 f: impl BindDispatch<'a, Brand, A, B, FA, Marker>,
677 ) -> Apply!(<Brand as Kind!( type Of<'a, T: 'a>: 'a; )>::Of<'a, B>) {
678 f.dispatch(ma)
679 }
680
681 #[document_signature]
687 #[document_type_parameters(
689 "The lifetime of the values.",
690 "The higher-kinded type brand.",
691 "The input element type.",
692 "The output element type.",
693 "The container type (owned or borrowed), inferred from the argument.",
694 "Marker type, inferred from the closure."
695 )]
696 #[document_parameters(
698 "The function to apply to each element.",
699 "The monadic value to bind over (owned for Val, borrowed for Ref)."
700 )]
701 #[document_returns("The result of binding the function over the value.")]
703 #[document_examples]
704 pub fn bind_flipped<'a, Brand: Kind_cdc7cd43dac7585f, A: 'a, B: 'a, FA, Marker>(
716 f: impl BindDispatch<'a, Brand, A, B, FA, Marker>,
717 ma: FA,
718 ) -> Apply!(<Brand as Kind!( type Of<'a, T: 'a>: 'a; )>::Of<'a, B>) {
719 f.dispatch(ma)
720 }
721
722 #[document_signature]
734 #[document_type_parameters(
736 "The lifetime of the values.",
737 "The brand of the monad.",
738 "The type of the value(s) inside the inner layer.",
739 "Dispatch marker type, inferred automatically."
740 )]
741 #[document_parameters("The nested monadic value (owned or borrowed).")]
743 #[document_returns("A container with one layer of nesting removed.")]
745 #[document_examples]
747 pub fn join<'a, Brand: Kind_cdc7cd43dac7585f, A: 'a, Marker>(
764 mma: impl JoinDispatch<'a, Brand, A, Marker>
765 ) -> Apply!(<Brand as Kind!( type Of<'a, T: 'a>: 'a; )>::Of<'a, A>) {
766 mma.dispatch()
767 }
768 }
769}
770
771pub use inner::*;