1#[fp_macros::document_module]
6mod inner {
7 use {
8 crate::{
9 Apply,
10 brands::{
11 PairBrand,
12 PairFirstAppliedBrand,
13 PairSecondAppliedBrand,
14 },
15 classes::*,
16 dispatch::Ref,
17 impl_kind,
18 kinds::*,
19 },
20 core::ops::ControlFlow,
21 fp_macros::*,
22 };
23
24 #[document_type_parameters("The type of the first value.", "The type of the second value.")]
39 #[cfg_attr(feature = "serde", derive(serde::Serialize, serde::Deserialize))]
41 #[derive(Clone, Copy, Debug, Default, Eq, Hash, Ord, PartialEq, PartialOrd)]
42 pub struct Pair<First, Second>(
43 pub First,
45 pub Second,
47 );
48
49 impl_kind! {
50 for PairBrand {
51 type Of<First,Second> = Pair<First, Second>;
52 }
53 }
54
55 impl_kind! {
56 for PairBrand {
57 type Of<'a, First: 'a, Second: 'a>: 'a = Pair<First, Second>;
58 }
59 }
60
61 #[document_type_parameters("The type of the first value.", "The type of the second value.")]
62 #[document_parameters("The pair instance.")]
63 impl<First, Second> Pair<First, Second> {
64 #[document_signature]
68 #[document_type_parameters(
70 "The type of the mapped first value.",
71 "The type of the mapped second value."
72 )]
73 #[document_parameters(
75 "The function to apply to the first value.",
76 "The function to apply to the second value."
77 )]
78 #[document_returns("A new pair containing the mapped values.")]
80 #[document_examples]
82 pub fn bimap<B, D>(
90 self,
91 f: impl FnOnce(First) -> B,
92 g: impl FnOnce(Second) -> D,
93 ) -> Pair<B, D> {
94 Pair(f(self.0), g(self.1))
95 }
96
97 #[document_signature]
101 #[document_type_parameters("The type of the mapped first value.")]
103 #[document_parameters("The function to apply to the first value.")]
105 #[document_returns("A new pair with the transformed first value.")]
107 #[document_examples]
109 pub fn map_first<B>(
117 self,
118 f: impl FnOnce(First) -> B,
119 ) -> Pair<B, Second> {
120 Pair(f(self.0), self.1)
121 }
122
123 #[document_signature]
127 #[document_type_parameters("The type of the mapped second value.")]
129 #[document_parameters("The function to apply to the second value.")]
131 #[document_returns("A new pair with the transformed second value.")]
133 #[document_examples]
135 pub fn map_second<D>(
143 self,
144 g: impl FnOnce(Second) -> D,
145 ) -> Pair<First, D> {
146 Pair(self.0, g(self.1))
147 }
148
149 #[document_signature]
154 #[document_type_parameters("The result type.")]
156 #[document_parameters(
158 "The function to apply to the first value.",
159 "The function to apply to the second value.",
160 "The function to combine the results."
161 )]
162 #[document_returns("The combined result.")]
164 #[document_examples]
166 pub fn fold<C>(
175 self,
176 f: impl FnOnce(First) -> C,
177 g: impl FnOnce(Second) -> C,
178 combine: impl FnOnce(C, C) -> C,
179 ) -> C {
180 combine(f(self.0), g(self.1))
181 }
182
183 #[document_signature]
187 #[document_type_parameters("The accumulator type.")]
189 #[document_parameters(
191 "The step function for the first value.",
192 "The step function for the second value.",
193 "The initial accumulator."
194 )]
195 #[document_returns("The result of folding: `f(first, g(second, z))`.")]
197 #[document_examples]
199 pub fn bi_fold_right<C>(
207 self,
208 f: impl FnOnce(First, C) -> C,
209 g: impl FnOnce(Second, C) -> C,
210 z: C,
211 ) -> C {
212 f(self.0, g(self.1, z))
213 }
214
215 #[document_signature]
219 #[document_type_parameters("The accumulator type.")]
221 #[document_parameters(
223 "The step function for the first value.",
224 "The step function for the second value.",
225 "The initial accumulator."
226 )]
227 #[document_returns("The result of folding: `g(f(z, first), second)`.")]
229 #[document_examples]
231 pub fn bi_fold_left<C>(
239 self,
240 f: impl FnOnce(C, First) -> C,
241 g: impl FnOnce(C, Second) -> C,
242 z: C,
243 ) -> C {
244 g(f(z, self.0), self.1)
245 }
246
247 #[document_signature]
251 #[document_type_parameters("The monoid type.")]
253 #[document_parameters(
255 "The function mapping the first value to the monoid.",
256 "The function mapping the second value to the monoid."
257 )]
258 #[document_returns("The combined monoid value.")]
260 #[document_examples]
262 pub fn bi_fold_map<M: Semigroup>(
270 self,
271 f: impl FnOnce(First) -> M,
272 g: impl FnOnce(Second) -> M,
273 ) -> M {
274 Semigroup::append(f(self.0), g(self.1))
275 }
276 }
277
278 #[document_type_parameters(
279 "The lifetime of the values.",
280 "The type of the first value.",
281 "The type of the second value."
282 )]
283 #[document_parameters("The pair instance.")]
284 impl<'a, First: 'a, Second: 'a> Pair<First, Second> {
285 #[document_signature]
289 #[document_type_parameters(
291 "The output type for the first value.",
292 "The output type for the second value.",
293 "The applicative context."
294 )]
295 #[document_parameters(
297 "The function for the first value.",
298 "The function for the second value."
299 )]
300 #[document_returns("A pair of the transformed values wrapped in the applicative context.")]
302 #[document_examples]
304 pub fn bi_traverse<C: 'a + Clone, D: 'a + Clone, F: Applicative>(
316 self,
317 f: impl Fn(First) -> Apply!(<F as Kind!( type Of<'a, T: 'a>: 'a; )>::Of<'a, C>) + 'a,
318 g: impl Fn(Second) -> Apply!(<F as Kind!( type Of<'a, T: 'a>: 'a; )>::Of<'a, D>) + 'a,
319 ) -> Apply!(<F as Kind!( type Of<'a, T: 'a>: 'a; )>::Of<'a, Pair<C, D>>)
320 where
321 Pair<C, D>: Clone, {
322 F::lift2(|c, d| Pair(c, d), f(self.0), g(self.1))
323 }
324 }
325
326 #[document_type_parameters("The type of the first value.", "The type of the second value.")]
327 #[document_parameters("The pair instance.")]
328 impl<First: Semigroup, Second> Pair<First, Second> {
329 #[document_signature]
334 #[document_type_parameters("The type of the new second value.")]
336 #[document_parameters("The function to apply to the second value.")]
338 #[document_returns(
340 "A new pair where the first values are combined and the second value is transformed."
341 )]
342 #[document_examples]
344 pub fn bind<C>(
354 self,
355 f: impl FnOnce(Second) -> Pair<First, C>,
356 ) -> Pair<First, C> {
357 let Pair(first, second) = self;
358 let Pair(next_first, next_second) = f(second);
359 Pair(Semigroup::append(first, next_first), next_second)
360 }
361 }
362
363 #[document_type_parameters("The type of the first value.", "The type of the second value.")]
364 #[document_parameters("The pair instance.")]
365 impl<First, Second: Semigroup> Pair<First, Second> {
366 #[document_signature]
371 #[document_type_parameters("The type of the new first value.")]
373 #[document_parameters("The function to apply to the first value.")]
375 #[document_returns(
377 "A new pair where the first value is transformed and the second values are combined."
378 )]
379 #[document_examples]
381 pub fn bind_first<C>(
391 self,
392 f: impl FnOnce(First) -> Pair<C, Second>,
393 ) -> Pair<C, Second> {
394 let Pair(first, second) = self;
395 let Pair(next_first, next_second) = f(first);
396 Pair(next_first, Semigroup::append(second, next_second))
397 }
398 }
399
400 impl Bifunctor for PairBrand {
401 #[document_signature]
405 #[document_type_parameters(
407 "The lifetime of the values.",
408 "The type of the first value.",
409 "The type of the mapped first value.",
410 "The type of the second value.",
411 "The type of the mapped second value."
412 )]
413 #[document_parameters(
415 "The function to apply to the first value.",
416 "The function to apply to the second value.",
417 "The pair to map over."
418 )]
419 #[document_returns("A new pair containing the mapped values.")]
421 #[document_examples]
422 fn bimap<'a, A: 'a, B: 'a, C: 'a, D: 'a>(
437 f: impl Fn(A) -> B + 'a,
438 g: impl Fn(C) -> D + 'a,
439 p: Apply!(<Self as Kind!( type Of<'a, A: 'a, B: 'a>: 'a; )>::Of<'a, A, C>),
440 ) -> Apply!(<Self as Kind!( type Of<'a, A: 'a, B: 'a>: 'a; )>::Of<'a, B, D>) {
441 p.bimap(f, g)
442 }
443 }
444
445 impl RefBifunctor for PairBrand {
446 #[document_signature]
452 #[document_type_parameters(
454 "The lifetime of the values.",
455 "The type of the first value.",
456 "The type of the mapped first value.",
457 "The type of the second value.",
458 "The type of the mapped second value."
459 )]
460 #[document_parameters(
462 "The function to apply to a reference of the first value.",
463 "The function to apply to a reference of the second value.",
464 "The pair to map over by reference."
465 )]
466 #[document_returns("A new pair containing the mapped values.")]
468 #[document_examples]
469 fn ref_bimap<'a, A: 'a, B: 'a, C: 'a, D: 'a>(
481 f: impl Fn(&A) -> B + 'a,
482 g: impl Fn(&C) -> D + 'a,
483 p: &Apply!(<Self as Kind!( type Of<'a, A: 'a, B: 'a>: 'a; )>::Of<'a, A, C>),
484 ) -> Apply!(<Self as Kind!( type Of<'a, A: 'a, B: 'a>: 'a; )>::Of<'a, B, D>) {
485 Pair(f(&p.0), g(&p.1))
486 }
487 }
488
489 impl RefBifoldable for PairBrand {
490 #[document_signature]
494 #[document_type_parameters(
496 "The lifetime of the values.",
497 "The brand of the cloneable function to use.",
498 "The type of the first value.",
499 "The type of the second value.",
500 "The accumulator type."
501 )]
502 #[document_parameters(
504 "The step function for a reference to the first value.",
505 "The step function for a reference to the second value.",
506 "The initial accumulator.",
507 "The pair to fold by reference."
508 )]
509 #[document_returns("`f(&a, g(&b, z))`.")]
511 #[document_examples]
512 fn ref_bi_fold_right<'a, FnBrand: LiftFn + 'a, A: 'a + Clone, B: 'a + Clone, C: 'a>(
532 f: impl Fn(&A, C) -> C + 'a,
533 g: impl Fn(&B, C) -> C + 'a,
534 z: C,
535 p: &Apply!(<Self as Kind!( type Of<'a, A: 'a, B: 'a>: 'a; )>::Of<'a, A, B>),
536 ) -> C {
537 f(&p.0, g(&p.1, z))
538 }
539 }
540
541 impl RefBitraversable for PairBrand {
542 #[document_signature]
547 #[document_type_parameters(
549 "The lifetime of the values.",
550 "The brand of the cloneable function wrapper.",
551 "The type of the first value.",
552 "The type of the second value.",
553 "The output type for the first value.",
554 "The output type for the second value.",
555 "The applicative context."
556 )]
557 #[document_parameters(
559 "The function applied to a reference to the first value.",
560 "The function applied to a reference to the second value.",
561 "The pair to traverse by reference."
562 )]
563 #[document_returns("`lift2(Pair, f(&a), g(&b))`.")]
565 #[document_examples]
566 fn ref_bi_traverse<
585 'a,
586 FnBrand,
587 A: 'a + Clone,
588 B: 'a + Clone,
589 C: 'a + Clone,
590 D: 'a + Clone,
591 F: Applicative,
592 >(
593 f: impl Fn(&A) -> Apply!(<F as Kind!( type Of<'a, T: 'a>: 'a; )>::Of<'a, C>) + 'a,
594 g: impl Fn(&B) -> Apply!(<F as Kind!( type Of<'a, T: 'a>: 'a; )>::Of<'a, D>) + 'a,
595 p: &Apply!(<Self as Kind!( type Of<'a, A: 'a, B: 'a>: 'a; )>::Of<'a, A, B>),
596 ) -> Apply!(<F as Kind!( type Of<'a, T: 'a>: 'a; )>::Of<'a, Apply!(<Self as Kind!( type Of<'a, A: 'a, B: 'a>: 'a; )>::Of<'a, C, D>)>)
597 where
598 FnBrand: LiftFn + 'a,
599 Apply!(<Self as Kind!( type Of<'a, A: 'a, B: 'a>: 'a; )>::Of<'a, C, D>): Clone,
600 Apply!(<F as Kind!( type Of<'a, T: 'a>: 'a; )>::Of<'a, C>): Clone,
601 Apply!(<F as Kind!( type Of<'a, T: 'a>: 'a; )>::Of<'a, D>): Clone, {
602 F::lift2(|c, d| Pair(c, d), f(&p.0), g(&p.1))
603 }
604 }
605
606 impl Bifoldable for PairBrand {
607 #[document_signature]
611 #[document_type_parameters(
613 "The lifetime of the values.",
614 "The brand of the cloneable function to use.",
615 "The type of the first value.",
616 "The type of the second value.",
617 "The accumulator type."
618 )]
619 #[document_parameters(
621 "The step function for the first value.",
622 "The step function for the second value.",
623 "The initial accumulator.",
624 "The pair to fold."
625 )]
626 #[document_returns("`f(a, g(b, z))`.")]
628 #[document_examples]
629 fn bi_fold_right<'a, FnBrand: CloneFn + 'a, A: 'a + Clone, B: 'a + Clone, C: 'a>(
648 f: impl Fn(A, C) -> C + 'a,
649 g: impl Fn(B, C) -> C + 'a,
650 z: C,
651 p: Apply!(<Self as Kind!( type Of<'a, A: 'a, B: 'a>: 'a; )>::Of<'a, A, B>),
652 ) -> C {
653 p.bi_fold_right(f, g, z)
654 }
655
656 #[document_signature]
660 #[document_type_parameters(
662 "The lifetime of the values.",
663 "The brand of the cloneable function to use.",
664 "The type of the first value.",
665 "The type of the second value.",
666 "The accumulator type."
667 )]
668 #[document_parameters(
670 "The step function for the first value.",
671 "The step function for the second value.",
672 "The initial accumulator.",
673 "The pair to fold."
674 )]
675 #[document_returns("`g(f(z, a), b)`.")]
677 #[document_examples]
678 fn bi_fold_left<'a, FnBrand: CloneFn + 'a, A: 'a + Clone, B: 'a + Clone, C: 'a>(
697 f: impl Fn(C, A) -> C + 'a,
698 g: impl Fn(C, B) -> C + 'a,
699 z: C,
700 p: Apply!(<Self as Kind!( type Of<'a, A: 'a, B: 'a>: 'a; )>::Of<'a, A, B>),
701 ) -> C {
702 p.bi_fold_left(f, g, z)
703 }
704
705 #[document_signature]
709 #[document_type_parameters(
711 "The lifetime of the values.",
712 "The brand of the cloneable function to use.",
713 "The type of the first value.",
714 "The type of the second value.",
715 "The monoid type."
716 )]
717 #[document_parameters(
719 "The function mapping the first value to the monoid.",
720 "The function mapping the second value to the monoid.",
721 "The pair to fold."
722 )]
723 #[document_returns("`Semigroup::append(f(a), g(b))`.")]
725 #[document_examples]
726 fn bi_fold_map<'a, FnBrand: CloneFn + 'a, A: 'a + Clone, B: 'a + Clone, M>(
743 f: impl Fn(A) -> M + 'a,
744 g: impl Fn(B) -> M + 'a,
745 p: Apply!(<Self as Kind!( type Of<'a, A: 'a, B: 'a>: 'a; )>::Of<'a, A, B>),
746 ) -> M
747 where
748 M: Monoid + 'a, {
749 p.bi_fold_map(f, g)
750 }
751 }
752
753 impl Bitraversable for PairBrand {
754 #[document_signature]
759 #[document_type_parameters(
761 "The lifetime of the values.",
762 "The type of the first value.",
763 "The type of the second value.",
764 "The output type for the first value.",
765 "The output type for the second value.",
766 "The applicative context."
767 )]
768 #[document_parameters(
770 "The function applied to the first value.",
771 "The function applied to the second value.",
772 "The pair to traverse."
773 )]
774 #[document_returns("`lift2(Pair, f(a), g(b))`.")]
776 #[document_examples]
777 fn bi_traverse<
795 'a,
796 A: 'a + Clone,
797 B: 'a + Clone,
798 C: 'a + Clone,
799 D: 'a + Clone,
800 F: Applicative,
801 >(
802 f: impl Fn(A) -> Apply!(<F as Kind!( type Of<'a, T: 'a>: 'a; )>::Of<'a, C>) + 'a,
803 g: impl Fn(B) -> Apply!(<F as Kind!( type Of<'a, T: 'a>: 'a; )>::Of<'a, D>) + 'a,
804 p: Apply!(<Self as Kind!( type Of<'a, A: 'a, B: 'a>: 'a; )>::Of<'a, A, B>),
805 ) -> Apply!(<F as Kind!( type Of<'a, T: 'a>: 'a; )>::Of<'a, Apply!(<Self as Kind!( type Of<'a, A: 'a, B: 'a>: 'a; )>::Of<'a, C, D>)>)
806 {
807 p.bi_traverse::<C, D, F>(f, g)
808 }
809 }
810
811 impl_kind! {
814 #[no_inferable_brand]
815 #[document_type_parameters("The type of the first value in the pair.")]
816 impl<First: 'static> for PairFirstAppliedBrand<First> {
817 type Of<'a, A: 'a>: 'a = Pair<First, A>;
818 }
819 }
820
821 #[document_type_parameters("The type of the first value in the pair.")]
822 impl<First: 'static> Functor for PairFirstAppliedBrand<First> {
823 #[document_signature]
827 #[document_type_parameters(
829 "The lifetime of the values.",
830 "The type of the second value.",
831 "The type of the result of applying the function."
832 )]
833 #[document_parameters(
835 "The function to apply to the second value.",
836 "The pair to map over."
837 )]
838 #[document_returns(
840 "A new pair containing the result of applying the function to the second value."
841 )]
842 #[document_examples]
843 fn map<'a, A: 'a, B: 'a>(
857 func: impl Fn(A) -> B + 'a,
858 fa: Apply!(<Self as Kind!( type Of<'a, T: 'a>: 'a; )>::Of<'a, A>),
859 ) -> Apply!(<Self as Kind!( type Of<'a, T: 'a>: 'a; )>::Of<'a, B>) {
860 fa.map_second(func)
861 }
862 }
863
864 #[document_type_parameters("The type of the first value in the pair.")]
865 impl<First: Clone + 'static> Lift for PairFirstAppliedBrand<First>
866 where
867 First: Semigroup,
868 {
869 #[document_signature]
873 #[document_type_parameters(
875 "The lifetime of the values.",
876 "The type of the first second value.",
877 "The type of the second second value.",
878 "The type of the result second value."
879 )]
880 #[document_parameters(
882 "The binary function to apply to the second values.",
883 "The first pair.",
884 "The second pair."
885 )]
886 #[document_returns(
888 "A new pair where the first values are combined using `Semigroup::append` and the second values are combined using `f`."
889 )]
890 #[document_examples]
891 fn lift2<'a, A, B, C>(
909 func: impl Fn(A, B) -> C + 'a,
910 fa: Apply!(<Self as Kind!( type Of<'a, T: 'a>: 'a; )>::Of<'a, A>),
911 fb: Apply!(<Self as Kind!( type Of<'a, T: 'a>: 'a; )>::Of<'a, B>),
912 ) -> Apply!(<Self as Kind!( type Of<'a, T: 'a>: 'a; )>::Of<'a, C>)
913 where
914 A: Clone + 'a,
915 B: Clone + 'a,
916 C: 'a, {
917 let Pair(fa_first, fa_second) = fa;
918 let Pair(fb_first, fb_second) = fb;
919 Pair(Semigroup::append(fa_first, fb_first), func(fa_second, fb_second))
920 }
921 }
922
923 #[document_type_parameters("The type of the first value in the pair.")]
924 impl<First: Clone + 'static> Pointed for PairFirstAppliedBrand<First>
925 where
926 First: Monoid,
927 {
928 #[document_signature]
932 #[document_type_parameters("The lifetime of the value.", "The type of the value to wrap.")]
934 #[document_parameters("The value to wrap.")]
936 #[document_returns("A pair containing the empty value of the first type and `a`.")]
938 #[document_examples]
940 fn pure<'a, A: 'a>(a: A) -> Apply!(<Self as Kind!( type Of<'a, T: 'a>: 'a; )>::Of<'a, A>) {
951 Pair(Monoid::empty(), a)
952 }
953 }
954
955 #[document_type_parameters("The type of the first value in the pair.")]
956 impl<First: Clone + Semigroup + 'static> ApplyFirst for PairFirstAppliedBrand<First> {}
957
958 #[document_type_parameters("The type of the first value in the pair.")]
959 impl<First: Clone + Semigroup + 'static> ApplySecond for PairFirstAppliedBrand<First> {}
960
961 #[document_type_parameters("The type of the first value in the pair.")]
962 impl<First: Clone + 'static> Semiapplicative for PairFirstAppliedBrand<First>
963 where
964 First: Semigroup,
965 {
966 #[document_signature]
970 #[document_type_parameters(
972 "The lifetime of the values.",
973 "The brand of the cloneable function wrapper.",
974 "The type of the input value.",
975 "The type of the output value."
976 )]
977 #[document_parameters(
979 "The pair containing the function.",
980 "The pair containing the value."
981 )]
982 #[document_returns(
984 "A new pair where the first values are combined and the function is applied to the second value."
985 )]
986 #[document_examples]
987 fn apply<'a, FnBrand: 'a + CloneFn, A: 'a + Clone, B: 'a>(
1002 ff: Apply!(<Self as Kind!( type Of<'a, T: 'a>: 'a; )>::Of<'a, <FnBrand as CloneFn>::Of<'a, A, B>>),
1003 fa: Apply!(<Self as Kind!( type Of<'a, T: 'a>: 'a; )>::Of<'a, A>),
1004 ) -> Apply!(<Self as Kind!( type Of<'a, T: 'a>: 'a; )>::Of<'a, B>) {
1005 Pair(Semigroup::append(ff.0, fa.0), ff.1(fa.1))
1006 }
1007 }
1008
1009 #[document_type_parameters("The type of the first value in the pair.")]
1010 impl<First: Clone + 'static> Semimonad for PairFirstAppliedBrand<First>
1011 where
1012 First: Semigroup,
1013 {
1014 #[document_signature]
1018 #[document_type_parameters(
1020 "The lifetime of the values.",
1021 "The type of the result of the first computation.",
1022 "The type of the result of the second computation."
1023 )]
1024 #[document_parameters("The first pair.", "The function to apply to the second value.")]
1026 #[document_returns("A new pair where the first values are combined.")]
1028 #[document_examples]
1030 fn bind<'a, A: 'a, B: 'a>(
1047 ma: Apply!(<Self as Kind!( type Of<'a, T: 'a>: 'a; )>::Of<'a, A>),
1048 func: impl Fn(A) -> Apply!(<Self as Kind!( type Of<'a, T: 'a>: 'a; )>::Of<'a, B>) + 'a,
1049 ) -> Apply!(<Self as Kind!( type Of<'a, T: 'a>: 'a; )>::Of<'a, B>) {
1050 ma.bind(func)
1051 }
1052 }
1053
1054 #[document_type_parameters("The type of the first value in the pair.")]
1056 impl<First: Clone + 'static> MonadRec for PairFirstAppliedBrand<First>
1057 where
1058 First: Monoid,
1059 {
1060 #[document_signature]
1068 #[document_type_parameters(
1070 "The lifetime of the computation.",
1071 "The type of the initial value and loop state.",
1072 "The type of the result."
1073 )]
1074 #[document_parameters("The step function.", "The initial value.")]
1076 #[document_returns("A pair with the accumulated first value and the final result.")]
1078 #[document_examples]
1080 fn tail_rec_m<'a, A: 'a, B: 'a>(
1104 func: impl Fn(
1105 A,
1106 )
1107 -> Apply!(<Self as Kind!( type Of<'a, T: 'a>: 'a; )>::Of<'a, ControlFlow<B, A>>)
1108 + 'a,
1109 initial: A,
1110 ) -> Apply!(<Self as Kind!( type Of<'a, T: 'a>: 'a; )>::Of<'a, B>) {
1111 let mut acc: First = Monoid::empty();
1112 let mut current = initial;
1113 loop {
1114 let Pair(first, step) = func(current);
1115 acc = Semigroup::append(acc, first);
1116 match step {
1117 ControlFlow::Continue(next) => current = next,
1118 ControlFlow::Break(b) => return Pair(acc, b),
1119 }
1120 }
1121 }
1122 }
1123
1124 #[document_type_parameters("The type of the first value in the pair.")]
1125 impl<First: 'static> Foldable for PairFirstAppliedBrand<First> {
1126 #[document_signature]
1130 #[document_type_parameters(
1132 "The lifetime of the values.",
1133 "The brand of the cloneable function to use.",
1134 "The type of the elements in the structure.",
1135 "The type of the accumulator."
1136 )]
1137 #[document_parameters("The folding function.", "The initial value.", "The pair to fold.")]
1139 #[document_returns("`func(a, initial)`.")]
1141 #[document_examples]
1143 fn fold_right<'a, FnBrand, A: 'a + Clone, B: 'a>(
1161 func: impl Fn(A, B) -> B + 'a,
1162 initial: B,
1163 fa: Apply!(<Self as Kind!( type Of<'a, T: 'a>: 'a; )>::Of<'a, A>),
1164 ) -> B
1165 where
1166 FnBrand: CloneFn + 'a, {
1167 func(fa.1, initial)
1168 }
1169
1170 #[document_signature]
1174 #[document_type_parameters(
1176 "The lifetime of the values.",
1177 "The brand of the cloneable function to use.",
1178 "The type of the elements in the structure.",
1179 "The type of the accumulator."
1180 )]
1181 #[document_parameters(
1183 "The function to apply to the accumulator and each element.",
1184 "The initial value of the accumulator.",
1185 "The identity to fold."
1186 )]
1187 #[document_returns("`func(initial, a)`.")]
1189 #[document_examples]
1190 fn fold_left<'a, FnBrand, A: 'a + Clone, B: 'a>(
1208 func: impl Fn(B, A) -> B + 'a,
1209 initial: B,
1210 fa: Apply!(<Self as Kind!( type Of<'a, T: 'a>: 'a; )>::Of<'a, A>),
1211 ) -> B
1212 where
1213 FnBrand: CloneFn + 'a, {
1214 func(initial, fa.1)
1215 }
1216
1217 #[document_signature]
1221 #[document_type_parameters(
1223 "The lifetime of the values.",
1224 "The brand of the cloneable function to use.",
1225 "The type of the elements in the structure.",
1226 "The type of the monoid."
1227 )]
1228 #[document_parameters("The mapping function.", "The pair to fold.")]
1230 #[document_returns("`func(a)`.")]
1232 #[document_examples]
1234 fn fold_map<'a, FnBrand, A: 'a + Clone, M>(
1251 func: impl Fn(A) -> M + 'a,
1252 fa: Apply!(<Self as Kind!( type Of<'a, T: 'a>: 'a; )>::Of<'a, A>),
1253 ) -> M
1254 where
1255 M: Monoid + 'a,
1256 FnBrand: CloneFn + 'a, {
1257 func(fa.1)
1258 }
1259 }
1260
1261 #[document_type_parameters("The type of the first value in the pair.")]
1262 impl<First: Clone + 'static> Traversable for PairFirstAppliedBrand<First> {
1263 #[document_signature]
1267 #[document_type_parameters(
1269 "The lifetime of the values.",
1270 "The type of the elements in the traversable structure.",
1271 "The type of the elements in the resulting traversable structure.",
1272 "The applicative context."
1273 )]
1274 #[document_parameters(
1276 "The function to apply to each element, returning a value in an applicative context.",
1277 "The pair to traverse."
1278 )]
1279 #[document_returns("The pair wrapped in the applicative context.")]
1281 #[document_examples]
1282 fn traverse<'a, A: 'a + Clone, B: 'a + Clone, F: Applicative>(
1299 func: impl Fn(A) -> Apply!(<F as Kind!( type Of<'a, T: 'a>: 'a; )>::Of<'a, B>) + 'a,
1300 ta: Apply!(<Self as Kind!( type Of<'a, T: 'a>: 'a; )>::Of<'a, A>),
1301 ) -> Apply!(<F as Kind!( type Of<'a, T: 'a>: 'a; )>::Of<'a, Apply!(<Self as Kind!( type Of<'a, T: 'a>: 'a; )>::Of<'a, B>)>)
1302 where
1303 Apply!(<Self as Kind!( type Of<'a, T: 'a>: 'a; )>::Of<'a, B>): Clone, {
1304 let Pair(first, second) = ta;
1305 F::map(move |b| Pair(first.clone(), b), func(second))
1306 }
1307
1308 #[document_signature]
1312 #[document_type_parameters(
1314 "The lifetime of the values.",
1315 "The type of the elements in the traversable structure.",
1316 "The applicative context."
1317 )]
1318 #[document_parameters("The pair containing the applicative value.")]
1320 #[document_returns("The pair wrapped in the applicative context.")]
1322 #[document_examples]
1324 fn sequence<'a, A: 'a + Clone, F: Applicative>(
1338 ta: Apply!(<Self as Kind!( type Of<'a, T: 'a>: 'a; )>::Of<'a, Apply!(<F as Kind!( type Of<'a, T: 'a>: 'a; )>::Of<'a, A>)>)
1339 ) -> Apply!(<F as Kind!( type Of<'a, T: 'a>: 'a; )>::Of<'a, Apply!(<Self as Kind!( type Of<'a, T: 'a>: 'a; )>::Of<'a, A>)>)
1340 where
1341 Apply!(<F as Kind!( type Of<'a, T: 'a>: 'a; )>::Of<'a, A>): Clone,
1342 Apply!(<Self as Kind!( type Of<'a, T: 'a>: 'a; )>::Of<'a, A>): Clone, {
1343 let Pair(first, second) = ta;
1344 F::map(move |a| Pair(first.clone(), a), second)
1345 }
1346 }
1347
1348 #[document_type_parameters("The type of the first value in the pair.")]
1351 impl<First: Clone + 'static> RefFunctor for PairFirstAppliedBrand<First> {
1352 #[document_signature]
1354 #[document_type_parameters("The lifetime.", "The input type.", "The output type.")]
1355 #[document_parameters("The function.", "The pair.")]
1356 #[document_returns("A new pair with the mapped second value.")]
1357 #[document_examples]
1358 fn ref_map<'a, A: 'a, B: 'a>(
1371 func: impl Fn(&A) -> B + 'a,
1372 fa: &Apply!(<Self as Kind!( type Of<'a, T: 'a>: 'a; )>::Of<'a, A>),
1373 ) -> Apply!(<Self as Kind!( type Of<'a, T: 'a>: 'a; )>::Of<'a, B>) {
1374 Pair(fa.0.clone(), func(&fa.1))
1375 }
1376 }
1377
1378 #[document_type_parameters("The type of the first value in the pair.")]
1379 impl<First: Clone + 'static> RefFoldable for PairFirstAppliedBrand<First> {
1380 #[document_signature]
1382 #[document_type_parameters(
1383 "The lifetime.",
1384 "The brand.",
1385 "The element type.",
1386 "The monoid type."
1387 )]
1388 #[document_parameters("The mapping function.", "The pair.")]
1389 #[document_returns("The monoid value.")]
1390 #[document_examples]
1391 fn ref_fold_map<'a, FnBrand, A: 'a + Clone, M>(
1405 func: impl Fn(&A) -> M + 'a,
1406 fa: &Apply!(<Self as Kind!( type Of<'a, T: 'a>: 'a; )>::Of<'a, A>),
1407 ) -> M
1408 where
1409 FnBrand: LiftFn + 'a,
1410 M: Monoid + 'a, {
1411 func(&fa.1)
1412 }
1413 }
1414
1415 #[document_type_parameters("The type of the first value in the pair.")]
1416 impl<First: Clone + 'static> RefTraversable for PairFirstAppliedBrand<First> {
1417 #[document_signature]
1419 #[document_type_parameters(
1420 "The lifetime.",
1421 "The brand.",
1422 "The input type.",
1423 "The output type.",
1424 "The applicative."
1425 )]
1426 #[document_parameters("The function.", "The pair.")]
1427 #[document_returns("The traversed result.")]
1428 #[document_examples]
1429 fn ref_traverse<'a, FnBrand, A: 'a + Clone, B: 'a + Clone, F: Applicative>(
1444 func: impl Fn(&A) -> Apply!(<F as Kind!( type Of<'a, T: 'a>: 'a; )>::Of<'a, B>) + 'a,
1445 ta: &Apply!(<Self as Kind!( type Of<'a, T: 'a>: 'a; )>::Of<'a, A>),
1446 ) -> Apply!(<F as Kind!( type Of<'a, T: 'a>: 'a; )>::Of<'a, Apply!(<Self as Kind!( type Of<'a, T: 'a>: 'a; )>::Of<'a, B>)>)
1447 where
1448 FnBrand: LiftFn + 'a,
1449 Apply!(<Self as Kind!( type Of<'a, T: 'a>: 'a; )>::Of<'a, B>): Clone,
1450 Apply!(<F as Kind!( type Of<'a, T: 'a>: 'a; )>::Of<'a, B>): Clone, {
1451 let first = ta.0.clone();
1452 F::map(move |b| Pair(first.clone(), b), func(&ta.1))
1453 }
1454 }
1455
1456 #[document_type_parameters("The type of the first value in the pair.")]
1457 impl<First: Clone + 'static> RefPointed for PairFirstAppliedBrand<First>
1458 where
1459 First: Monoid,
1460 {
1461 #[document_signature]
1463 #[document_type_parameters("The lifetime.", "The value type.")]
1464 #[document_parameters("The reference to wrap.")]
1465 #[document_returns("A pair containing `Monoid::empty()` and a clone of the value.")]
1466 #[document_examples]
1467 fn ref_pure<'a, A: Clone + 'a>(
1480 a: &A
1481 ) -> Apply!(<Self as Kind!( type Of<'a, T: 'a>: 'a; )>::Of<'a, A>) {
1482 Pair(Monoid::empty(), a.clone())
1483 }
1484 }
1485
1486 #[document_type_parameters("The type of the first value in the pair.")]
1487 impl<First: Clone + 'static> RefLift for PairFirstAppliedBrand<First>
1488 where
1489 First: Semigroup,
1490 {
1491 #[document_signature]
1493 #[document_type_parameters("The lifetime.", "First input.", "Second input.", "Output.")]
1494 #[document_parameters("The binary function.", "The first pair.", "The second pair.")]
1495 #[document_returns("A pair with combined first values and the function result.")]
1496 #[document_examples]
1497 fn ref_lift2<'a, A: 'a, B: 'a, C: 'a>(
1513 func: impl Fn(&A, &B) -> C + 'a,
1514 fa: &Apply!(<Self as Kind!( type Of<'a, T: 'a>: 'a; )>::Of<'a, A>),
1515 fb: &Apply!(<Self as Kind!( type Of<'a, T: 'a>: 'a; )>::Of<'a, B>),
1516 ) -> Apply!(<Self as Kind!( type Of<'a, T: 'a>: 'a; )>::Of<'a, C>) {
1517 Pair(Semigroup::append(fa.0.clone(), fb.0.clone()), func(&fa.1, &fb.1))
1518 }
1519 }
1520
1521 #[document_type_parameters("The type of the first value in the pair.")]
1522 impl<First: Clone + 'static> RefSemiapplicative for PairFirstAppliedBrand<First>
1523 where
1524 First: Semigroup,
1525 {
1526 #[document_signature]
1528 #[document_type_parameters(
1529 "The lifetime.",
1530 "The function brand.",
1531 "The input type.",
1532 "The output type."
1533 )]
1534 #[document_parameters(
1535 "The pair containing the function.",
1536 "The pair containing the value."
1537 )]
1538 #[document_returns("A pair with combined first values and the function result.")]
1539 #[document_examples]
1540 fn ref_apply<'a, FnBrand: 'a + CloneFn<Ref>, A: 'a, B: 'a>(
1556 ff: &Apply!(<Self as Kind!( type Of<'a, T: 'a>: 'a; )>::Of<'a, <FnBrand as CloneFn<Ref>>::Of<'a, A, B>>),
1557 fa: &Apply!(<Self as Kind!( type Of<'a, T: 'a>: 'a; )>::Of<'a, A>),
1558 ) -> Apply!(<Self as Kind!( type Of<'a, T: 'a>: 'a; )>::Of<'a, B>) {
1559 Pair(Semigroup::append(ff.0.clone(), fa.0.clone()), (*ff.1)(&fa.1))
1560 }
1561 }
1562
1563 #[document_type_parameters("The type of the first value in the pair.")]
1564 impl<First: Clone + 'static> RefSemimonad for PairFirstAppliedBrand<First>
1565 where
1566 First: Semigroup,
1567 {
1568 #[document_signature]
1570 #[document_type_parameters("The lifetime.", "The input type.", "The output type.")]
1571 #[document_parameters("The input pair.", "The function to apply by reference.")]
1572 #[document_returns("A pair with combined first values.")]
1573 #[document_examples]
1574 fn ref_bind<'a, A: 'a, B: 'a>(
1589 fa: &Apply!(<Self as Kind!( type Of<'a, T: 'a>: 'a; )>::Of<'a, A>),
1590 f: impl Fn(&A) -> Apply!(<Self as Kind!( type Of<'a, T: 'a>: 'a; )>::Of<'a, B>) + 'a,
1591 ) -> Apply!(<Self as Kind!( type Of<'a, T: 'a>: 'a; )>::Of<'a, B>) {
1592 let Pair(next_first, next_second) = f(&fa.1);
1593 Pair(Semigroup::append(fa.0.clone(), next_first), next_second)
1594 }
1595 }
1596
1597 impl_kind! {
1600 #[no_inferable_brand]
1601 #[document_type_parameters("The type of the second value in the pair.")]
1602 impl<Second: 'static> for PairSecondAppliedBrand<Second> {
1603 type Of<'a, A: 'a>: 'a = Pair<A, Second>;
1604 }
1605 }
1606
1607 #[document_type_parameters("The type of the second value in the pair.")]
1608 impl<Second: 'static> Functor for PairSecondAppliedBrand<Second> {
1609 #[document_signature]
1613 #[document_type_parameters(
1615 "The lifetime of the values.",
1616 "The type of the first value.",
1617 "The type of the result of applying the function."
1618 )]
1619 #[document_parameters("The function to apply to the first value.", "The pair to map over.")]
1621 #[document_returns(
1623 "A new pair containing the result of applying the function to the first value."
1624 )]
1625 #[document_examples]
1627 fn map<'a, A: 'a, B: 'a>(
1641 func: impl Fn(A) -> B + 'a,
1642 fa: Apply!(<Self as Kind!( type Of<'a, T: 'a>: 'a; )>::Of<'a, A>),
1643 ) -> Apply!(<Self as Kind!( type Of<'a, T: 'a>: 'a; )>::Of<'a, B>) {
1644 fa.map_first(func)
1645 }
1646 }
1647
1648 #[document_type_parameters("The type of the second value in the pair.")]
1649 impl<Second: Clone + 'static> Lift for PairSecondAppliedBrand<Second>
1650 where
1651 Second: Semigroup,
1652 {
1653 #[document_signature]
1657 #[document_type_parameters(
1659 "The lifetime of the values.",
1660 "The type of the first first value.",
1661 "The type of the second first value.",
1662 "The type of the result first value."
1663 )]
1664 #[document_parameters(
1666 "The binary function to apply to the first values.",
1667 "The first pair.",
1668 "The second pair."
1669 )]
1670 #[document_returns(
1672 "A new pair where the first values are combined using `f` and the second values are combined using `Semigroup::append`."
1673 )]
1674 #[document_examples]
1675 fn lift2<'a, A, B, C>(
1693 func: impl Fn(A, B) -> C + 'a,
1694 fa: Apply!(<Self as Kind!( type Of<'a, T: 'a>: 'a; )>::Of<'a, A>),
1695 fb: Apply!(<Self as Kind!( type Of<'a, T: 'a>: 'a; )>::Of<'a, B>),
1696 ) -> Apply!(<Self as Kind!( type Of<'a, T: 'a>: 'a; )>::Of<'a, C>)
1697 where
1698 A: Clone + 'a,
1699 B: Clone + 'a,
1700 C: 'a, {
1701 Pair(func(fa.0, fb.0), Semigroup::append(fa.1, fb.1))
1702 }
1703 }
1704
1705 #[document_type_parameters("The type of the second value in the pair.")]
1706 impl<Second: Clone + 'static> Pointed for PairSecondAppliedBrand<Second>
1707 where
1708 Second: Monoid,
1709 {
1710 #[document_signature]
1714 #[document_type_parameters("The lifetime of the value.", "The type of the value to wrap.")]
1716 #[document_parameters("The value to wrap.")]
1718 #[document_returns("A pair containing `a` and the empty value of the second type.")]
1720 #[document_examples]
1722 fn pure<'a, A: 'a>(a: A) -> Apply!(<Self as Kind!( type Of<'a, T: 'a>: 'a; )>::Of<'a, A>) {
1733 Pair(a, Monoid::empty())
1734 }
1735 }
1736
1737 #[document_type_parameters("The type of the second value in the pair.")]
1738 impl<Second: Clone + Semigroup + 'static> ApplyFirst for PairSecondAppliedBrand<Second> {}
1739
1740 #[document_type_parameters("The type of the second value in the pair.")]
1741 impl<Second: Clone + Semigroup + 'static> ApplySecond for PairSecondAppliedBrand<Second> {}
1742
1743 #[document_type_parameters("The type of the second value in the pair.")]
1744 impl<Second: Clone + 'static> Semiapplicative for PairSecondAppliedBrand<Second>
1745 where
1746 Second: Semigroup,
1747 {
1748 #[document_signature]
1752 #[document_type_parameters(
1754 "The lifetime of the values.",
1755 "The brand of the cloneable function wrapper.",
1756 "The type of the input value.",
1757 "The type of the output value."
1758 )]
1759 #[document_parameters(
1761 "The pair containing the function (in Err).",
1762 "The pair containing the value (in Err)."
1763 )]
1764 #[document_returns(
1766 "`Err(f(a))` if both are `Err`, otherwise the first success encountered."
1767 )]
1768 #[document_examples]
1769 fn apply<'a, FnBrand: 'a + CloneFn, A: 'a + Clone, B: 'a>(
1784 ff: Apply!(<Self as Kind!( type Of<'a, T: 'a>: 'a; )>::Of<'a, <FnBrand as CloneFn>::Of<'a, A, B>>),
1785 fa: Apply!(<Self as Kind!( type Of<'a, T: 'a>: 'a; )>::Of<'a, A>),
1786 ) -> Apply!(<Self as Kind!( type Of<'a, T: 'a>: 'a; )>::Of<'a, B>) {
1787 Pair(ff.0(fa.0), Semigroup::append(ff.1, fa.1))
1788 }
1789 }
1790
1791 #[document_type_parameters("The type of the second value in the pair.")]
1792 impl<Second: Clone + 'static> Semimonad for PairSecondAppliedBrand<Second>
1793 where
1794 Second: Semigroup,
1795 {
1796 #[document_signature]
1800 #[document_type_parameters(
1802 "The lifetime of the values.",
1803 "The type of the result of the first computation.",
1804 "The type of the result of the second computation."
1805 )]
1806 #[document_parameters("The first result.", "The function to apply to the error value.")]
1808 #[document_returns(
1810 "The result of applying `f` to the error if `ma` is `Err`, otherwise the original success."
1811 )]
1812 #[document_examples]
1814 fn bind<'a, A: 'a, B: 'a>(
1831 ma: Apply!(<Self as Kind!( type Of<'a, T: 'a>: 'a; )>::Of<'a, A>),
1832 func: impl Fn(A) -> Apply!(<Self as Kind!( type Of<'a, T: 'a>: 'a; )>::Of<'a, B>) + 'a,
1833 ) -> Apply!(<Self as Kind!( type Of<'a, T: 'a>: 'a; )>::Of<'a, B>) {
1834 ma.bind_first(func)
1835 }
1836 }
1837
1838 #[document_type_parameters("The type of the second value in the pair.")]
1840 impl<Second: Clone + 'static> MonadRec for PairSecondAppliedBrand<Second>
1841 where
1842 Second: Monoid,
1843 {
1844 #[document_signature]
1852 #[document_type_parameters(
1854 "The lifetime of the computation.",
1855 "The type of the initial value and loop state.",
1856 "The type of the result."
1857 )]
1858 #[document_parameters("The step function.", "The initial value.")]
1860 #[document_returns("A pair with the final result and the accumulated second value.")]
1862 #[document_examples]
1864 fn tail_rec_m<'a, A: 'a, B: 'a>(
1888 func: impl Fn(
1889 A,
1890 )
1891 -> Apply!(<Self as Kind!( type Of<'a, T: 'a>: 'a; )>::Of<'a, ControlFlow<B, A>>)
1892 + 'a,
1893 initial: A,
1894 ) -> Apply!(<Self as Kind!( type Of<'a, T: 'a>: 'a; )>::Of<'a, B>) {
1895 let mut acc: Second = Monoid::empty();
1896 let mut current = initial;
1897 loop {
1898 let Pair(step, second) = func(current);
1899 acc = Semigroup::append(acc, second);
1900 match step {
1901 ControlFlow::Continue(next) => current = next,
1902 ControlFlow::Break(b) => return Pair(b, acc),
1903 }
1904 }
1905 }
1906 }
1907
1908 #[document_type_parameters("The type of the second value in the pair.")]
1909 impl<Second: 'static> Foldable for PairSecondAppliedBrand<Second> {
1910 #[document_signature]
1914 #[document_type_parameters(
1916 "The lifetime of the values.",
1917 "The brand of the cloneable function to use.",
1918 "The type of the elements in the structure.",
1919 "The type of the accumulator."
1920 )]
1921 #[document_parameters("The folding function.", "The initial value.", "The result to fold.")]
1923 #[document_returns("`func(a, initial)` if `fa` is `Err(a)`, otherwise `initial`.")]
1925 #[document_examples]
1927 fn fold_right<'a, FnBrand, A: 'a + Clone, B: 'a>(
1945 func: impl Fn(A, B) -> B + 'a,
1946 initial: B,
1947 fa: Apply!(<Self as Kind!( type Of<'a, T: 'a>: 'a; )>::Of<'a, A>),
1948 ) -> B
1949 where
1950 FnBrand: CloneFn + 'a, {
1951 func(fa.0, initial)
1952 }
1953
1954 #[document_signature]
1958 #[document_type_parameters(
1960 "The lifetime of the values.",
1961 "The brand of the cloneable function to use.",
1962 "The type of the elements in the structure.",
1963 "The type of the accumulator."
1964 )]
1965 #[document_parameters("The folding function.", "The initial value.", "The result to fold.")]
1967 #[document_returns("`func(initial, a)` if `fa` is `Err(a)`, otherwise `initial`.")]
1969 #[document_examples]
1971 fn fold_left<'a, FnBrand, A: 'a + Clone, B: 'a>(
1989 func: impl Fn(B, A) -> B + 'a,
1990 initial: B,
1991 fa: Apply!(<Self as Kind!( type Of<'a, T: 'a>: 'a; )>::Of<'a, A>),
1992 ) -> B
1993 where
1994 FnBrand: CloneFn + 'a, {
1995 func(initial, fa.0)
1996 }
1997
1998 #[document_signature]
2002 #[document_type_parameters(
2004 "The lifetime of the values.",
2005 "The brand of the cloneable function to use.",
2006 "The type of the elements in the structure.",
2007 "The type of the monoid."
2008 )]
2009 #[document_parameters("The mapping function.", "The result to fold.")]
2011 #[document_returns("`func(a)` if `fa` is `Err(a)`, otherwise `M::empty()`.")]
2013 #[document_examples]
2015 fn fold_map<'a, FnBrand, A: 'a + Clone, M>(
2032 func: impl Fn(A) -> M + 'a,
2033 fa: Apply!(<Self as Kind!( type Of<'a, T: 'a>: 'a; )>::Of<'a, A>),
2034 ) -> M
2035 where
2036 M: Monoid + 'a,
2037 FnBrand: CloneFn + 'a, {
2038 func(fa.0)
2039 }
2040 }
2041
2042 #[document_type_parameters("The type of the second value in the pair.")]
2043 impl<Second: Clone + 'static> Traversable for PairSecondAppliedBrand<Second> {
2044 #[document_signature]
2048 #[document_type_parameters(
2050 "The lifetime of the values.",
2051 "The type of the elements in the traversable structure.",
2052 "The type of the elements in the resulting traversable structure.",
2053 "The applicative context."
2054 )]
2055 #[document_parameters("The function to apply.", "The result to traverse.")]
2057 #[document_returns("The result wrapped in the applicative context.")]
2059 #[document_examples]
2061 fn traverse<'a, A: 'a + Clone, B: 'a + Clone, F: Applicative>(
2078 func: impl Fn(A) -> Apply!(<F as Kind!( type Of<'a, T: 'a>: 'a; )>::Of<'a, B>) + 'a,
2079 ta: Apply!(<Self as Kind!( type Of<'a, T: 'a>: 'a; )>::Of<'a, A>),
2080 ) -> Apply!(<F as Kind!( type Of<'a, T: 'a>: 'a; )>::Of<'a, Apply!(<Self as Kind!( type Of<'a, T: 'a>: 'a; )>::Of<'a, B>)>)
2081 where
2082 Apply!(<Self as Kind!( type Of<'a, T: 'a>: 'a; )>::Of<'a, B>): Clone, {
2083 let Pair(first, second) = ta;
2084 F::map(move |b| Pair(b, second.clone()), func(first))
2085 }
2086
2087 #[document_signature]
2091 #[document_type_parameters(
2093 "The lifetime of the values.",
2094 "The type of the elements in the traversable structure.",
2095 "The applicative context."
2096 )]
2097 #[document_parameters("The result containing the applicative value.")]
2099 #[document_returns("The result wrapped in the applicative context.")]
2101 #[document_examples]
2103 fn sequence<'a, A: 'a + Clone, F: Applicative>(
2117 ta: Apply!(<Self as Kind!( type Of<'a, T: 'a>: 'a; )>::Of<'a, Apply!(<F as Kind!( type Of<'a, T: 'a>: 'a; )>::Of<'a, A>)>)
2118 ) -> Apply!(<F as Kind!( type Of<'a, T: 'a>: 'a; )>::Of<'a, Apply!(<Self as Kind!( type Of<'a, T: 'a>: 'a; )>::Of<'a, A>)>)
2119 where
2120 Apply!(<F as Kind!( type Of<'a, T: 'a>: 'a; )>::Of<'a, A>): Clone,
2121 Apply!(<Self as Kind!( type Of<'a, T: 'a>: 'a; )>::Of<'a, A>): Clone, {
2122 let Pair(first, second) = ta;
2123 F::map(move |a| Pair(a, second.clone()), first)
2124 }
2125 }
2126 #[document_type_parameters("The type of the second value in the pair.")]
2129 impl<Second: Clone + 'static> RefFunctor for PairSecondAppliedBrand<Second> {
2130 #[document_signature]
2132 #[document_type_parameters("The lifetime.", "The input type.", "The output type.")]
2133 #[document_parameters("The function.", "The pair.")]
2134 #[document_returns("A new pair with the mapped first value.")]
2135 #[document_examples]
2136 fn ref_map<'a, A: 'a, B: 'a>(
2149 func: impl Fn(&A) -> B + 'a,
2150 fa: &Apply!(<Self as Kind!( type Of<'a, T: 'a>: 'a; )>::Of<'a, A>),
2151 ) -> Apply!(<Self as Kind!( type Of<'a, T: 'a>: 'a; )>::Of<'a, B>) {
2152 Pair(func(&fa.0), fa.1.clone())
2153 }
2154 }
2155
2156 #[document_type_parameters("The type of the second value in the pair.")]
2157 impl<Second: Clone + 'static> RefFoldable for PairSecondAppliedBrand<Second> {
2158 #[document_signature]
2160 #[document_type_parameters(
2161 "The lifetime.",
2162 "The brand.",
2163 "The element type.",
2164 "The monoid type."
2165 )]
2166 #[document_parameters("The mapping function.", "The pair.")]
2167 #[document_returns("The monoid value.")]
2168 #[document_examples]
2169 fn ref_fold_map<'a, FnBrand, A: 'a + Clone, M>(
2183 func: impl Fn(&A) -> M + 'a,
2184 fa: &Apply!(<Self as Kind!( type Of<'a, T: 'a>: 'a; )>::Of<'a, A>),
2185 ) -> M
2186 where
2187 FnBrand: LiftFn + 'a,
2188 M: Monoid + 'a, {
2189 func(&fa.0)
2190 }
2191 }
2192
2193 #[document_type_parameters("The type of the second value in the pair.")]
2194 impl<Second: Clone + 'static> RefTraversable for PairSecondAppliedBrand<Second> {
2195 #[document_signature]
2197 #[document_type_parameters(
2198 "The lifetime.",
2199 "The brand.",
2200 "The input type.",
2201 "The output type.",
2202 "The applicative."
2203 )]
2204 #[document_parameters("The function.", "The pair.")]
2205 #[document_returns("The traversed result.")]
2206 #[document_examples]
2207 fn ref_traverse<'a, FnBrand, A: 'a + Clone, B: 'a + Clone, F: Applicative>(
2222 func: impl Fn(&A) -> Apply!(<F as Kind!( type Of<'a, T: 'a>: 'a; )>::Of<'a, B>) + 'a,
2223 ta: &Apply!(<Self as Kind!( type Of<'a, T: 'a>: 'a; )>::Of<'a, A>),
2224 ) -> Apply!(<F as Kind!( type Of<'a, T: 'a>: 'a; )>::Of<'a, Apply!(<Self as Kind!( type Of<'a, T: 'a>: 'a; )>::Of<'a, B>)>)
2225 where
2226 FnBrand: LiftFn + 'a,
2227 Apply!(<Self as Kind!( type Of<'a, T: 'a>: 'a; )>::Of<'a, B>): Clone,
2228 Apply!(<F as Kind!( type Of<'a, T: 'a>: 'a; )>::Of<'a, B>): Clone, {
2229 let second = ta.1.clone();
2230 F::map(move |a| Pair(a, second.clone()), func(&ta.0))
2231 }
2232 }
2233
2234 #[document_type_parameters("The type of the second value in the pair.")]
2235 impl<Second: Clone + 'static> RefPointed for PairSecondAppliedBrand<Second>
2236 where
2237 Second: Monoid,
2238 {
2239 #[document_signature]
2241 #[document_type_parameters("The lifetime.", "The value type.")]
2242 #[document_parameters("The reference to wrap.")]
2243 #[document_returns("A pair containing a clone of the value and `Monoid::empty()`.")]
2244 #[document_examples]
2245 fn ref_pure<'a, A: Clone + 'a>(
2258 a: &A
2259 ) -> Apply!(<Self as Kind!( type Of<'a, T: 'a>: 'a; )>::Of<'a, A>) {
2260 Pair(a.clone(), Monoid::empty())
2261 }
2262 }
2263
2264 #[document_type_parameters("The type of the second value in the pair.")]
2265 impl<Second: Clone + 'static> RefLift for PairSecondAppliedBrand<Second>
2266 where
2267 Second: Semigroup,
2268 {
2269 #[document_signature]
2271 #[document_type_parameters("The lifetime.", "First input.", "Second input.", "Output.")]
2272 #[document_parameters("The binary function.", "The first pair.", "The second pair.")]
2273 #[document_returns("A pair with the function result and combined second values.")]
2274 #[document_examples]
2275 fn ref_lift2<'a, A: 'a, B: 'a, C: 'a>(
2291 func: impl Fn(&A, &B) -> C + 'a,
2292 fa: &Apply!(<Self as Kind!( type Of<'a, T: 'a>: 'a; )>::Of<'a, A>),
2293 fb: &Apply!(<Self as Kind!( type Of<'a, T: 'a>: 'a; )>::Of<'a, B>),
2294 ) -> Apply!(<Self as Kind!( type Of<'a, T: 'a>: 'a; )>::Of<'a, C>) {
2295 Pair(func(&fa.0, &fb.0), Semigroup::append(fa.1.clone(), fb.1.clone()))
2296 }
2297 }
2298
2299 #[document_type_parameters("The type of the second value in the pair.")]
2300 impl<Second: Clone + 'static> RefSemiapplicative for PairSecondAppliedBrand<Second>
2301 where
2302 Second: Semigroup,
2303 {
2304 #[document_signature]
2306 #[document_type_parameters(
2307 "The lifetime.",
2308 "The function brand.",
2309 "The input type.",
2310 "The output type."
2311 )]
2312 #[document_parameters(
2313 "The pair containing the function.",
2314 "The pair containing the value."
2315 )]
2316 #[document_returns("A pair with the function result and combined second values.")]
2317 #[document_examples]
2318 fn ref_apply<'a, FnBrand: 'a + CloneFn<Ref>, A: 'a, B: 'a>(
2334 ff: &Apply!(<Self as Kind!( type Of<'a, T: 'a>: 'a; )>::Of<'a, <FnBrand as CloneFn<Ref>>::Of<'a, A, B>>),
2335 fa: &Apply!(<Self as Kind!( type Of<'a, T: 'a>: 'a; )>::Of<'a, A>),
2336 ) -> Apply!(<Self as Kind!( type Of<'a, T: 'a>: 'a; )>::Of<'a, B>) {
2337 Pair((*ff.0)(&fa.0), Semigroup::append(ff.1.clone(), fa.1.clone()))
2338 }
2339 }
2340
2341 #[document_type_parameters("The type of the second value in the pair.")]
2342 impl<Second: Clone + 'static> RefSemimonad for PairSecondAppliedBrand<Second>
2343 where
2344 Second: Semigroup,
2345 {
2346 #[document_signature]
2348 #[document_type_parameters("The lifetime.", "The input type.", "The output type.")]
2349 #[document_parameters("The input pair.", "The function to apply by reference.")]
2350 #[document_returns("A pair with combined second values.")]
2351 #[document_examples]
2352 fn ref_bind<'a, A: 'a, B: 'a>(
2367 fa: &Apply!(<Self as Kind!( type Of<'a, T: 'a>: 'a; )>::Of<'a, A>),
2368 f: impl Fn(&A) -> Apply!(<Self as Kind!( type Of<'a, T: 'a>: 'a; )>::Of<'a, B>) + 'a,
2369 ) -> Apply!(<Self as Kind!( type Of<'a, T: 'a>: 'a; )>::Of<'a, B>) {
2370 let Pair(next_first, next_second) = f(&fa.0);
2371 Pair(next_first, Semigroup::append(fa.1.clone(), next_second))
2372 }
2373 }
2374}
2375pub use inner::*;
2376
2377#[cfg(test)]
2378mod tests {
2379 use {
2380 super::inner::*,
2381 crate::{
2382 brands::*,
2383 classes::*,
2384 functions::*,
2385 },
2386 quickcheck_macros::quickcheck,
2387 };
2388
2389 #[test]
2393 fn test_bimap() {
2394 let x = Pair(1, 5);
2395 assert_eq!(
2396 explicit::bimap::<PairBrand, _, _, _, _, _, _>((|a| a + 1, |b| b * 2), x),
2397 Pair(2, 10)
2398 );
2399 }
2400
2401 #[quickcheck]
2405 fn bifunctor_identity(
2406 first: String,
2407 second: i32,
2408 ) -> bool {
2409 let x = Pair(first, second);
2410 explicit::bimap::<PairBrand, _, _, _, _, _, _>((identity, identity), x.clone()) == x
2411 }
2412
2413 #[quickcheck]
2415 fn bifunctor_composition(
2416 first: i32,
2417 second: i32,
2418 ) -> bool {
2419 let x = Pair(first, second);
2420 let f = |x: i32| x.wrapping_add(1);
2421 let g = |x: i32| x.wrapping_mul(2);
2422 let h = |x: i32| x.wrapping_sub(1);
2423 let i = |x: i32| if x == 0 { 0 } else { x.wrapping_div(2) };
2424
2425 explicit::bimap::<PairBrand, _, _, _, _, _, _>((compose(f, g), compose(h, i)), x)
2426 == explicit::bimap::<PairBrand, _, _, _, _, _, _>(
2427 (f, h),
2428 explicit::bimap::<PairBrand, _, _, _, _, _, _>((g, i), x),
2429 )
2430 }
2431
2432 #[quickcheck]
2436 fn functor_identity(
2437 first: String,
2438 second: i32,
2439 ) -> bool {
2440 let x = Pair(first, second);
2441 explicit::map::<PairFirstAppliedBrand<String>, _, _, _, _>(identity, x.clone()) == x
2442 }
2443
2444 #[quickcheck]
2446 fn functor_composition(
2447 first: String,
2448 second: i32,
2449 ) -> bool {
2450 let x = Pair(first, second);
2451 let f = |x: i32| x.wrapping_add(1);
2452 let g = |x: i32| x.wrapping_mul(2);
2453 explicit::map::<PairFirstAppliedBrand<String>, _, _, _, _>(compose(f, g), x.clone())
2454 == explicit::map::<PairFirstAppliedBrand<String>, _, _, _, _>(
2455 f,
2456 explicit::map::<PairFirstAppliedBrand<String>, _, _, _, _>(g, x),
2457 )
2458 }
2459
2460 #[quickcheck]
2464 fn applicative_identity(
2465 first: String,
2466 second: i32,
2467 ) -> bool {
2468 let v = Pair(first, second);
2469 apply::<RcFnBrand, PairFirstAppliedBrand<String>, _, _>(
2470 pure::<PairFirstAppliedBrand<String>, _>(<RcFnBrand as LiftFn>::new(identity)),
2471 v.clone(),
2472 ) == v
2473 }
2474
2475 #[quickcheck]
2477 fn applicative_homomorphism(x: i32) -> bool {
2478 let f = |x: i32| x.wrapping_mul(2);
2479 apply::<RcFnBrand, PairFirstAppliedBrand<String>, _, _>(
2480 pure::<PairFirstAppliedBrand<String>, _>(<RcFnBrand as LiftFn>::new(f)),
2481 pure::<PairFirstAppliedBrand<String>, _>(x),
2482 ) == pure::<PairFirstAppliedBrand<String>, _>(f(x))
2483 }
2484
2485 #[quickcheck]
2487 fn applicative_composition(
2488 w_first: String,
2489 w_second: i32,
2490 u_seed: i32,
2491 v_seed: i32,
2492 ) -> bool {
2493 let w = Pair(w_first, w_second);
2494
2495 let u_fn = <RcFnBrand as LiftFn>::new(move |x: i32| x.wrapping_add(u_seed));
2496 let u = pure::<PairFirstAppliedBrand<String>, _>(u_fn);
2497
2498 let v_fn = <RcFnBrand as LiftFn>::new(move |x: i32| x.wrapping_mul(v_seed));
2499 let v = pure::<PairFirstAppliedBrand<String>, _>(v_fn);
2500
2501 let vw = apply::<RcFnBrand, PairFirstAppliedBrand<String>, _, _>(v.clone(), w.clone());
2503 let rhs = apply::<RcFnBrand, PairFirstAppliedBrand<String>, _, _>(u.clone(), vw);
2504
2505 let compose_fn = <RcFnBrand as LiftFn>::new(|f: std::rc::Rc<dyn Fn(i32) -> i32>| {
2507 let f = f.clone();
2508 <RcFnBrand as LiftFn>::new(move |g: std::rc::Rc<dyn Fn(i32) -> i32>| {
2509 let f = f.clone();
2510 let g = g.clone();
2511 <RcFnBrand as LiftFn>::new(move |x| f(g(x)))
2512 })
2513 });
2514
2515 let pure_compose = pure::<PairFirstAppliedBrand<String>, _>(compose_fn);
2516 let u_applied = apply::<RcFnBrand, PairFirstAppliedBrand<String>, _, _>(pure_compose, u);
2517 let uv = apply::<RcFnBrand, PairFirstAppliedBrand<String>, _, _>(u_applied, v);
2518 let lhs = apply::<RcFnBrand, PairFirstAppliedBrand<String>, _, _>(uv, w);
2519
2520 lhs == rhs
2521 }
2522
2523 #[quickcheck]
2525 fn applicative_interchange(
2526 y: i32,
2527 u_seed: i32,
2528 ) -> bool {
2529 let f = move |x: i32| x.wrapping_mul(u_seed);
2531 let u = pure::<PairFirstAppliedBrand<String>, _>(<RcFnBrand as LiftFn>::new(f));
2532
2533 let lhs = apply::<RcFnBrand, PairFirstAppliedBrand<String>, _, _>(
2534 u.clone(),
2535 pure::<PairFirstAppliedBrand<String>, _>(y),
2536 );
2537
2538 let rhs_fn = <RcFnBrand as LiftFn>::new(move |f: std::rc::Rc<dyn Fn(i32) -> i32>| f(y));
2539 let rhs = apply::<RcFnBrand, PairFirstAppliedBrand<String>, _, _>(
2540 pure::<PairFirstAppliedBrand<String>, _>(rhs_fn),
2541 u,
2542 );
2543
2544 lhs == rhs
2545 }
2546
2547 #[quickcheck]
2551 fn monad_left_identity(a: i32) -> bool {
2552 let f = |x: i32| Pair("f".to_string(), x.wrapping_mul(2));
2553 explicit::bind::<PairFirstAppliedBrand<String>, _, _, _, _>(
2554 pure::<PairFirstAppliedBrand<String>, _>(a),
2555 f,
2556 ) == f(a)
2557 }
2558
2559 #[quickcheck]
2561 fn monad_right_identity(
2562 first: String,
2563 second: i32,
2564 ) -> bool {
2565 let m = Pair(first, second);
2566 explicit::bind::<PairFirstAppliedBrand<String>, _, _, _, _>(
2567 m.clone(),
2568 pure::<PairFirstAppliedBrand<String>, _>,
2569 ) == m
2570 }
2571
2572 #[quickcheck]
2574 fn monad_associativity(
2575 first: String,
2576 second: i32,
2577 ) -> bool {
2578 let m = Pair(first, second);
2579 let f = |x: i32| Pair("f".to_string(), x.wrapping_mul(2));
2580 let g = |x: i32| Pair("g".to_string(), x.wrapping_add(1));
2581 explicit::bind::<PairFirstAppliedBrand<String>, _, _, _, _>(
2582 explicit::bind::<PairFirstAppliedBrand<String>, _, _, _, _>(m.clone(), f),
2583 g,
2584 ) == explicit::bind::<PairFirstAppliedBrand<String>, _, _, _, _>(m, |x| {
2585 explicit::bind::<PairFirstAppliedBrand<String>, _, _, _, _>(f(x), g)
2586 })
2587 }
2588
2589 #[quickcheck]
2593 fn monad_rec_first_applied_identity(x: i32) -> bool {
2594 use {
2595 crate::classes::monad_rec::tail_rec_m,
2596 core::ops::ControlFlow,
2597 };
2598 tail_rec_m::<PairFirstAppliedBrand<String>, _, _>(
2599 |a| Pair(String::new(), ControlFlow::Break(a)),
2600 x,
2601 ) == Pair(String::new(), x)
2602 }
2603
2604 #[test]
2606 fn monad_rec_first_applied_accumulation() {
2607 use {
2608 crate::classes::monad_rec::tail_rec_m,
2609 core::ops::ControlFlow,
2610 };
2611 let result = tail_rec_m::<PairFirstAppliedBrand<String>, _, _>(
2612 |n: i32| {
2613 if n < 3 {
2614 Pair(format!("{n},"), ControlFlow::Continue(n + 1))
2615 } else {
2616 Pair(format!("{n}"), ControlFlow::Break(n))
2617 }
2618 },
2619 0,
2620 );
2621 assert_eq!(result, Pair("0,1,2,3".to_string(), 3));
2622 }
2623
2624 #[test]
2626 fn monad_rec_first_applied_stack_safety() {
2627 use {
2628 crate::classes::monad_rec::tail_rec_m,
2629 core::ops::ControlFlow,
2630 };
2631 let iterations: i64 = 200_000;
2632 let result = tail_rec_m::<PairFirstAppliedBrand<Vec<()>>, _, _>(
2633 |acc| {
2634 if acc < iterations {
2635 Pair(vec![], ControlFlow::Continue(acc + 1))
2636 } else {
2637 Pair(vec![], ControlFlow::Break(acc))
2638 }
2639 },
2640 0i64,
2641 );
2642 assert_eq!(result, Pair(vec![], iterations));
2643 }
2644
2645 #[quickcheck]
2649 fn monad_rec_second_applied_identity(x: i32) -> bool {
2650 use {
2651 crate::classes::monad_rec::tail_rec_m,
2652 core::ops::ControlFlow,
2653 };
2654 tail_rec_m::<PairSecondAppliedBrand<String>, _, _>(
2655 |a| Pair(ControlFlow::Break(a), String::new()),
2656 x,
2657 ) == Pair(x, String::new())
2658 }
2659
2660 #[test]
2662 fn monad_rec_second_applied_accumulation() {
2663 use {
2664 crate::classes::monad_rec::tail_rec_m,
2665 core::ops::ControlFlow,
2666 };
2667 let result = tail_rec_m::<PairSecondAppliedBrand<String>, _, _>(
2668 |n: i32| {
2669 if n < 3 {
2670 Pair(ControlFlow::Continue(n + 1), format!("{n},"))
2671 } else {
2672 Pair(ControlFlow::Break(n), format!("{n}"))
2673 }
2674 },
2675 0,
2676 );
2677 assert_eq!(result, Pair(3, "0,1,2,3".to_string()));
2678 }
2679
2680 #[test]
2682 fn monad_rec_second_applied_stack_safety() {
2683 use {
2684 crate::classes::monad_rec::tail_rec_m,
2685 core::ops::ControlFlow,
2686 };
2687 let iterations: i64 = 200_000;
2688 let result = tail_rec_m::<PairSecondAppliedBrand<Vec<()>>, _, _>(
2689 |acc| {
2690 if acc < iterations {
2691 Pair(ControlFlow::Continue(acc + 1), vec![])
2692 } else {
2693 Pair(ControlFlow::Break(acc), vec![])
2694 }
2695 },
2696 0i64,
2697 );
2698 assert_eq!(result, Pair(iterations, vec![]));
2699 }
2700
2701 #[quickcheck]
2705 fn ref_bifunctor_identity(
2706 a: i32,
2707 b: i32,
2708 ) -> bool {
2709 let p = Pair(a, b);
2710 explicit::bimap::<PairBrand, _, _, _, _, _, _>((|x: &i32| *x, |x: &i32| *x), &p) == p
2711 }
2712
2713 #[quickcheck]
2715 fn ref_bifunctor_composition(
2716 a: i32,
2717 b: i32,
2718 ) -> bool {
2719 let p = Pair(a, b);
2720 let f1 = |x: &i32| x.wrapping_add(1);
2721 let f2 = |x: &i32| x.wrapping_mul(2);
2722 let g1 = |x: &i32| x.wrapping_add(10);
2723 let g2 = |x: &i32| x.wrapping_mul(3);
2724 explicit::bimap::<PairBrand, _, _, _, _, _, _>(
2725 (|x: &i32| f2(&f1(x)), |x: &i32| g2(&g1(x))),
2726 &p,
2727 ) == explicit::bimap::<PairBrand, _, _, _, _, _, _>(
2728 (f2, g2),
2729 &explicit::bimap::<PairBrand, _, _, _, _, _, _>((f1, g1), &p),
2730 )
2731 }
2732
2733 #[quickcheck]
2737 fn ref_bifoldable_fold_map(
2738 a: i32,
2739 b: i32,
2740 ) -> bool {
2741 let p = Pair(a, b);
2742 let result = explicit::bi_fold_map::<RcFnBrand, PairBrand, _, _, _, _, _>(
2743 (|x: &i32| x.to_string(), |x: &i32| x.to_string()),
2744 &p,
2745 );
2746 result == format!("{}{}", a, b)
2747 }
2748
2749 #[quickcheck]
2753 fn ref_bitraversable_consistency(
2754 a: i32,
2755 b: i32,
2756 ) -> bool {
2757 let p = Pair(a, b);
2758 let f = |x: &i32| Some(x.wrapping_add(1));
2759 let g = |x: &i32| Some(x.wrapping_mul(2));
2760 let traversed = explicit::bi_traverse::<RcFnBrand, PairBrand, _, _, _, _, OptionBrand, _, _>(
2761 (f, g),
2762 &p,
2763 );
2764 let mapped_then_sequenced =
2765 ref_bi_sequence::<PairBrand, RcFnBrand, _, _, OptionBrand>(&explicit::bimap::<
2766 PairBrand,
2767 _,
2768 _,
2769 _,
2770 _,
2771 _,
2772 _,
2773 >((f, g), &p));
2774 traversed == mapped_then_sequenced
2775 }
2776}