Skip to main content

fp_library/dispatch/
lift.rs

1//! Dispatch for [`Lift::lift2`](crate::classes::Lift::lift2) through
2//! [`explicit::lift5`], and their by-reference counterparts
3//! [`RefLift::ref_lift2`](crate::classes::RefLift::ref_lift2) etc.
4//!
5//! Provides `Lift2Dispatch` through `Lift5Dispatch` traits and unified
6//! [`explicit::lift2`] through [`explicit::lift5`] free functions.
7//!
8//! ### Examples
9//!
10//! ```
11//! use fp_library::{
12//! 	brands::*,
13//! 	functions::explicit::*,
14//! 	types::*,
15//! };
16//!
17//! let z = lift2::<OptionBrand, _, _, _, _, _, _>(|a, b| a + b, Some(1), Some(2));
18//! assert_eq!(z, Some(3));
19//!
20//! let x = RcLazy::pure(3);
21//! let y = RcLazy::pure(4);
22//! let z = lift2::<LazyBrand<RcLazyConfig>, _, _, _, _, _, _>(|a: &i32, b: &i32| *a + *b, &x, &y);
23//! assert_eq!(*z.evaluate(), 7);
24//! ```
25
26#[fp_macros::document_module]
27pub(crate) mod inner {
28	use {
29		crate::{
30			classes::{
31				Lift,
32				RefLift,
33			},
34			dispatch::{
35				Ref,
36				Val,
37			},
38			kinds::*,
39		},
40		fp_macros::*,
41	};
42
43	// -- Lift2Dispatch --
44
45	/// Trait that routes a lift2 operation to the appropriate type class method.
46	///
47	/// `Fn(A, B) -> C` resolves to [`Val`], `Fn(&A, &B) -> C` resolves to [`Ref`].
48	/// The `FA` and `FB` type parameters are inferred from the container arguments:
49	/// owned for Val dispatch, borrowed for Ref dispatch.
50	#[document_type_parameters(
51		"The lifetime of the values.",
52		"The brand of the context.",
53		"The type of the first value.",
54		"The type of the second value.",
55		"The type of the result.",
56		"The first container type (owned or borrowed), inferred from the argument.",
57		"The second container type (owned or borrowed), inferred from the argument.",
58		"Dispatch marker type, inferred automatically."
59	)]
60	#[document_parameters("The closure implementing this dispatch.")]
61	pub trait Lift2Dispatch<'a, Brand: Kind_cdc7cd43dac7585f, A: 'a, B: 'a, C: 'a, FA, FB, Marker> {
62		/// Perform the dispatched lift2 operation.
63		#[document_signature]
64		#[document_parameters("The first context.", "The second context.")]
65		#[document_returns("A new context containing the result.")]
66		#[document_examples]
67		///
68		/// ```
69		/// use fp_library::{
70		/// 	brands::*,
71		/// 	functions::explicit::*,
72		/// };
73		/// let z = lift2::<OptionBrand, _, _, _, _, _, _>(|a, b| a + b, Some(1), Some(2));
74		/// assert_eq!(z, Some(3));
75		/// ```
76		fn dispatch(
77			self,
78			fa: FA,
79			fb: FB,
80		) -> Apply!(<Brand as Kind!( type Of<'a, T: 'a>: 'a; )>::Of<'a, C>);
81	}
82
83	/// Routes `Fn(A, B) -> C` closures to [`Lift::lift2`].
84	#[document_type_parameters(
85		"The lifetime.",
86		"The brand.",
87		"The first type.",
88		"The second type.",
89		"The result type.",
90		"The closure type."
91	)]
92	#[document_parameters("The closure that takes owned values.")]
93	impl<'a, Brand, A, B, C, F>
94		Lift2Dispatch<
95			'a,
96			Brand,
97			A,
98			B,
99			C,
100			Apply!(<Brand as Kind!( type Of<'a, T: 'a>: 'a; )>::Of<'a, A>),
101			Apply!(<Brand as Kind!( type Of<'a, T: 'a>: 'a; )>::Of<'a, B>),
102			Val,
103		> for F
104	where
105		Brand: Lift,
106		A: Clone + 'a,
107		B: Clone + 'a,
108		C: 'a,
109		F: Fn(A, B) -> C + 'a,
110	{
111		#[document_signature]
112		#[document_parameters("The first context.", "The second context.")]
113		#[document_returns("A new context containing the result.")]
114		#[document_examples]
115		///
116		/// ```
117		/// use fp_library::{
118		/// 	brands::*,
119		/// 	functions::explicit::*,
120		/// };
121		/// let z = lift2::<OptionBrand, _, _, _, _, _, _>(|a, b| a + b, Some(1), Some(2));
122		/// assert_eq!(z, Some(3));
123		/// ```
124		fn dispatch(
125			self,
126			fa: Apply!(<Brand as Kind!( type Of<'a, T: 'a>: 'a; )>::Of<'a, A>),
127			fb: Apply!(<Brand as Kind!( type Of<'a, T: 'a>: 'a; )>::Of<'a, B>),
128		) -> Apply!(<Brand as Kind!( type Of<'a, T: 'a>: 'a; )>::Of<'a, C>) {
129			Brand::lift2(self, fa, fb)
130		}
131	}
132
133	/// Routes `Fn(&A, &B) -> C` closures to [`RefLift::ref_lift2`].
134	///
135	/// The containers must be passed by reference (`&fa`, `&fb`).
136	#[document_type_parameters(
137		"The lifetime.",
138		"The borrow lifetime.",
139		"The brand.",
140		"The first type.",
141		"The second type.",
142		"The result type.",
143		"The closure type."
144	)]
145	#[document_parameters("The closure that takes references.")]
146	impl<'a, 'b, Brand, A, B, C, F>
147		Lift2Dispatch<
148			'a,
149			Brand,
150			A,
151			B,
152			C,
153			&'b Apply!(<Brand as Kind!( type Of<'a, T: 'a>: 'a; )>::Of<'a, A>),
154			&'b Apply!(<Brand as Kind!( type Of<'a, T: 'a>: 'a; )>::Of<'a, B>),
155			Ref,
156		> for F
157	where
158		Brand: RefLift,
159		A: 'a,
160		B: 'a,
161		C: 'a,
162		F: Fn(&A, &B) -> C + 'a,
163	{
164		#[document_signature]
165		#[document_parameters(
166			"A reference to the first context.",
167			"A reference to the second context."
168		)]
169		#[document_returns("A new context containing the result.")]
170		#[document_examples]
171		///
172		/// ```
173		/// use fp_library::{
174		/// 	brands::*,
175		/// 	functions::explicit::*,
176		/// 	types::*,
177		/// };
178		/// let x = RcLazy::pure(3);
179		/// let y = RcLazy::pure(4);
180		/// let z = lift2::<LazyBrand<RcLazyConfig>, _, _, _, _, _, _>(|a: &i32, b: &i32| *a + *b, &x, &y);
181		/// assert_eq!(*z.evaluate(), 7);
182		/// ```
183		fn dispatch(
184			self,
185			fa: &'b Apply!(<Brand as Kind!( type Of<'a, T: 'a>: 'a; )>::Of<'a, A>),
186			fb: &'b Apply!(<Brand as Kind!( type Of<'a, T: 'a>: 'a; )>::Of<'a, B>),
187		) -> Apply!(<Brand as Kind!( type Of<'a, T: 'a>: 'a; )>::Of<'a, C>) {
188			Brand::ref_lift2(self, fa, fb)
189		}
190	}
191
192	// -- Lift3Dispatch --
193
194	/// Trait that routes a lift3 operation to the appropriate type class method.
195	#[document_type_parameters(
196		"The lifetime.",
197		"The brand.",
198		"First type.",
199		"Second type.",
200		"Third type.",
201		"Result type.",
202		"The first container type (owned or borrowed), inferred from the argument.",
203		"The second container type (owned or borrowed), inferred from the argument.",
204		"The third container type (owned or borrowed), inferred from the argument.",
205		"Dispatch marker."
206	)]
207	#[document_parameters("The closure implementing this dispatch.")]
208	pub trait Lift3Dispatch<
209		'a,
210		Brand: Kind_cdc7cd43dac7585f,
211		A: 'a,
212		B: 'a,
213		C: 'a,
214		D: 'a,
215		FA,
216		FB,
217		FC,
218		Marker,
219	> {
220		/// Perform the dispatched lift3 operation.
221		#[document_signature]
222		#[document_parameters("First context.", "Second context.", "Third context.")]
223		#[document_returns("A new context containing the result.")]
224		#[document_examples]
225		///
226		/// ```
227		/// use fp_library::{
228		/// 	brands::*,
229		/// 	functions::explicit::*,
230		/// };
231		/// let r = lift3::<OptionBrand, _, _, _, _, _, _, _, _>(
232		/// 	|a, b, c| a + b + c,
233		/// 	Some(1),
234		/// 	Some(2),
235		/// 	Some(3),
236		/// );
237		/// assert_eq!(r, Some(6));
238		/// ```
239		fn dispatch(
240			self,
241			fa: FA,
242			fb: FB,
243			fc: FC,
244		) -> Apply!(<Brand as Kind!( type Of<'a, T: 'a>: 'a; )>::Of<'a, D>);
245	}
246
247	/// Routes `Fn(A, B, C) -> D` closures through [`Lift::lift2`].
248	#[document_type_parameters(
249		"The lifetime.",
250		"The brand.",
251		"First.",
252		"Second.",
253		"Third.",
254		"Result.",
255		"Closure."
256	)]
257	#[document_parameters("The closure that takes owned values.")]
258	impl<'a, Brand, A, B, C, D, F>
259		Lift3Dispatch<
260			'a,
261			Brand,
262			A,
263			B,
264			C,
265			D,
266			Apply!(<Brand as Kind!( type Of<'a, T: 'a>: 'a; )>::Of<'a, A>),
267			Apply!(<Brand as Kind!( type Of<'a, T: 'a>: 'a; )>::Of<'a, B>),
268			Apply!(<Brand as Kind!( type Of<'a, T: 'a>: 'a; )>::Of<'a, C>),
269			Val,
270		> for F
271	where
272		Brand: Lift,
273		A: Clone + 'a,
274		B: Clone + 'a,
275		C: Clone + 'a,
276		D: 'a,
277		F: Fn(A, B, C) -> D + 'a,
278	{
279		#[document_signature]
280		#[document_parameters("First context.", "Second context.", "Third context.")]
281		#[document_returns("A new context containing the result.")]
282		#[document_examples]
283		///
284		/// ```
285		/// use fp_library::{
286		/// 	brands::*,
287		/// 	functions::explicit::*,
288		/// };
289		/// let r = lift3::<OptionBrand, _, _, _, _, _, _, _, _>(
290		/// 	|a, b, c| a + b + c,
291		/// 	Some(1),
292		/// 	Some(2),
293		/// 	Some(3),
294		/// );
295		/// assert_eq!(r, Some(6));
296		/// ```
297		fn dispatch(
298			self,
299			fa: Apply!(<Brand as Kind!( type Of<'a, T: 'a>: 'a; )>::Of<'a, A>),
300			fb: Apply!(<Brand as Kind!( type Of<'a, T: 'a>: 'a; )>::Of<'a, B>),
301			fc: Apply!(<Brand as Kind!( type Of<'a, T: 'a>: 'a; )>::Of<'a, C>),
302		) -> Apply!(<Brand as Kind!( type Of<'a, T: 'a>: 'a; )>::Of<'a, D>) {
303			Brand::lift2(move |(a, b), c| self(a, b, c), Brand::lift2(|a, b| (a, b), fa, fb), fc)
304		}
305	}
306
307	/// Routes `Fn(&A, &B, &C) -> D` closures through [`RefLift::ref_lift2`].
308	///
309	/// The containers must be passed by reference (`&fa`, `&fb`, `&fc`).
310	#[document_type_parameters(
311		"The lifetime.",
312		"The borrow lifetime.",
313		"The brand.",
314		"First.",
315		"Second.",
316		"Third.",
317		"Result.",
318		"Closure."
319	)]
320	#[document_parameters("The closure that takes references.")]
321	impl<'a, 'b, Brand, A, B, C, D, F>
322		Lift3Dispatch<
323			'a,
324			Brand,
325			A,
326			B,
327			C,
328			D,
329			&'b Apply!(<Brand as Kind!( type Of<'a, T: 'a>: 'a; )>::Of<'a, A>),
330			&'b Apply!(<Brand as Kind!( type Of<'a, T: 'a>: 'a; )>::Of<'a, B>),
331			&'b Apply!(<Brand as Kind!( type Of<'a, T: 'a>: 'a; )>::Of<'a, C>),
332			Ref,
333		> for F
334	where
335		Brand: RefLift,
336		A: Clone + 'a,
337		B: Clone + 'a,
338		C: 'a,
339		D: 'a,
340		F: Fn(&A, &B, &C) -> D + 'a,
341	{
342		#[document_signature]
343		#[document_parameters("First context.", "Second context.", "Third context.")]
344		#[document_returns("A new context containing the result.")]
345		#[document_examples]
346		///
347		/// ```
348		/// use fp_library::{
349		/// 	brands::*,
350		/// 	functions::explicit::*,
351		/// 	types::*,
352		/// };
353		/// let a = RcLazy::pure(1);
354		/// let b = RcLazy::pure(2);
355		/// let c = RcLazy::pure(3);
356		/// let r = lift3::<LazyBrand<RcLazyConfig>, _, _, _, _, _, _, _, _>(
357		/// 	|a: &i32, b: &i32, c: &i32| *a + *b + *c,
358		/// 	&a,
359		/// 	&b,
360		/// 	&c,
361		/// );
362		/// assert_eq!(*r.evaluate(), 6);
363		/// ```
364		fn dispatch(
365			self,
366			fa: &'b Apply!(<Brand as Kind!( type Of<'a, T: 'a>: 'a; )>::Of<'a, A>),
367			fb: &'b Apply!(<Brand as Kind!( type Of<'a, T: 'a>: 'a; )>::Of<'a, B>),
368			fc: &'b Apply!(<Brand as Kind!( type Of<'a, T: 'a>: 'a; )>::Of<'a, C>),
369		) -> Apply!(<Brand as Kind!( type Of<'a, T: 'a>: 'a; )>::Of<'a, D>) {
370			Brand::ref_lift2(
371				move |(a, b): &(A, B), c: &C| self(a, b, c),
372				&Brand::ref_lift2(|a: &A, b: &B| (a.clone(), b.clone()), fa, fb),
373				fc,
374			)
375		}
376	}
377
378	// -- Lift4Dispatch --
379
380	/// Trait that routes a lift4 operation to the appropriate type class method.
381	#[document_type_parameters(
382		"The lifetime.",
383		"The brand.",
384		"First.",
385		"Second.",
386		"Third.",
387		"Fourth.",
388		"Result.",
389		"The first container type (owned or borrowed), inferred from the argument.",
390		"The second container type (owned or borrowed), inferred from the argument.",
391		"The third container type (owned or borrowed), inferred from the argument.",
392		"The fourth container type (owned or borrowed), inferred from the argument.",
393		"Dispatch marker."
394	)]
395	#[document_parameters("The closure implementing this dispatch.")]
396	pub trait Lift4Dispatch<
397		'a,
398		Brand: Kind_cdc7cd43dac7585f,
399		A: 'a,
400		B: 'a,
401		C: 'a,
402		D: 'a,
403		E: 'a,
404		FA,
405		FB,
406		FC,
407		FD,
408		Marker,
409	> {
410		/// Perform the dispatched lift4 operation.
411		#[document_signature]
412		#[document_parameters("First.", "Second.", "Third.", "Fourth.")]
413		#[document_returns("Result context.")]
414		#[document_examples]
415		///
416		/// ```
417		/// use fp_library::{
418		/// 	brands::*,
419		/// 	functions::explicit::*,
420		/// };
421		/// let r = lift4::<OptionBrand, _, _, _, _, _, _, _, _, _, _>(
422		/// 	|a, b, c, d| a + b + c + d,
423		/// 	Some(1),
424		/// 	Some(2),
425		/// 	Some(3),
426		/// 	Some(4),
427		/// );
428		/// assert_eq!(r, Some(10));
429		/// ```
430		fn dispatch(
431			self,
432			fa: FA,
433			fb: FB,
434			fc: FC,
435			fd: FD,
436		) -> Apply!(<Brand as Kind!( type Of<'a, T: 'a>: 'a; )>::Of<'a, E>);
437	}
438
439	/// Routes `Fn(A, B, C, D) -> E` closures through [`Lift::lift2`].
440	#[document_type_parameters(
441		"The lifetime.",
442		"The brand.",
443		"First.",
444		"Second.",
445		"Third.",
446		"Fourth.",
447		"Result.",
448		"Closure."
449	)]
450	#[document_parameters("The closure that takes owned values.")]
451	impl<'a, Brand, A, B, C, D, E, Func>
452		Lift4Dispatch<
453			'a,
454			Brand,
455			A,
456			B,
457			C,
458			D,
459			E,
460			Apply!(<Brand as Kind!( type Of<'a, T: 'a>: 'a; )>::Of<'a, A>),
461			Apply!(<Brand as Kind!( type Of<'a, T: 'a>: 'a; )>::Of<'a, B>),
462			Apply!(<Brand as Kind!( type Of<'a, T: 'a>: 'a; )>::Of<'a, C>),
463			Apply!(<Brand as Kind!( type Of<'a, T: 'a>: 'a; )>::Of<'a, D>),
464			Val,
465		> for Func
466	where
467		Brand: Lift,
468		A: Clone + 'a,
469		B: Clone + 'a,
470		C: Clone + 'a,
471		D: Clone + 'a,
472		E: 'a,
473		Func: Fn(A, B, C, D) -> E + 'a,
474	{
475		#[document_signature]
476		#[document_parameters("First.", "Second.", "Third.", "Fourth.")]
477		#[document_returns("Result context.")]
478		#[document_examples]
479		///
480		/// ```
481		/// use fp_library::{
482		/// 	brands::*,
483		/// 	functions::explicit::*,
484		/// };
485		/// let r = lift4::<OptionBrand, _, _, _, _, _, _, _, _, _, _>(
486		/// 	|a, b, c, d| a + b + c + d,
487		/// 	Some(1),
488		/// 	Some(2),
489		/// 	Some(3),
490		/// 	Some(4),
491		/// );
492		/// assert_eq!(r, Some(10));
493		/// ```
494		fn dispatch(
495			self,
496			fa: Apply!(<Brand as Kind!( type Of<'a, T: 'a>: 'a; )>::Of<'a, A>),
497			fb: Apply!(<Brand as Kind!( type Of<'a, T: 'a>: 'a; )>::Of<'a, B>),
498			fc: Apply!(<Brand as Kind!( type Of<'a, T: 'a>: 'a; )>::Of<'a, C>),
499			fd: Apply!(<Brand as Kind!( type Of<'a, T: 'a>: 'a; )>::Of<'a, D>),
500		) -> Apply!(<Brand as Kind!( type Of<'a, T: 'a>: 'a; )>::Of<'a, E>) {
501			Brand::lift2(
502				move |((a, b), c), d| self(a, b, c, d),
503				Brand::lift2(move |(a, b), c| ((a, b), c), Brand::lift2(|a, b| (a, b), fa, fb), fc),
504				fd,
505			)
506		}
507	}
508
509	/// Routes `Fn(&A, &B, &C, &D) -> E` closures through [`RefLift::ref_lift2`].
510	///
511	/// The containers must be passed by reference.
512	#[document_type_parameters(
513		"The lifetime.",
514		"The borrow lifetime.",
515		"The brand.",
516		"First.",
517		"Second.",
518		"Third.",
519		"Fourth.",
520		"Result.",
521		"Closure."
522	)]
523	#[document_parameters("The closure that takes references.")]
524	impl<'a, 'b, Brand, A, B, C, D, E, Func>
525		Lift4Dispatch<
526			'a,
527			Brand,
528			A,
529			B,
530			C,
531			D,
532			E,
533			&'b Apply!(<Brand as Kind!( type Of<'a, T: 'a>: 'a; )>::Of<'a, A>),
534			&'b Apply!(<Brand as Kind!( type Of<'a, T: 'a>: 'a; )>::Of<'a, B>),
535			&'b Apply!(<Brand as Kind!( type Of<'a, T: 'a>: 'a; )>::Of<'a, C>),
536			&'b Apply!(<Brand as Kind!( type Of<'a, T: 'a>: 'a; )>::Of<'a, D>),
537			Ref,
538		> for Func
539	where
540		Brand: RefLift,
541		A: Clone + 'a,
542		B: Clone + 'a,
543		C: Clone + 'a,
544		D: 'a,
545		E: 'a,
546		Func: Fn(&A, &B, &C, &D) -> E + 'a,
547	{
548		#[document_signature]
549		#[document_parameters("First.", "Second.", "Third.", "Fourth.")]
550		#[document_returns("Result context.")]
551		#[document_examples]
552		///
553		/// ```
554		/// use fp_library::{
555		/// 	brands::*,
556		/// 	functions::explicit::*,
557		/// 	types::*,
558		/// };
559		/// let a = RcLazy::pure(1);
560		/// let b = RcLazy::pure(2);
561		/// let c = RcLazy::pure(3);
562		/// let d = RcLazy::pure(4);
563		/// let r = lift4::<LazyBrand<RcLazyConfig>, _, _, _, _, _, _, _, _, _, _>(
564		/// 	|a: &i32, b: &i32, c: &i32, d: &i32| *a + *b + *c + *d,
565		/// 	&a,
566		/// 	&b,
567		/// 	&c,
568		/// 	&d,
569		/// );
570		/// assert_eq!(*r.evaluate(), 10);
571		/// ```
572		fn dispatch(
573			self,
574			fa: &'b Apply!(<Brand as Kind!( type Of<'a, T: 'a>: 'a; )>::Of<'a, A>),
575			fb: &'b Apply!(<Brand as Kind!( type Of<'a, T: 'a>: 'a; )>::Of<'a, B>),
576			fc: &'b Apply!(<Brand as Kind!( type Of<'a, T: 'a>: 'a; )>::Of<'a, C>),
577			fd: &'b Apply!(<Brand as Kind!( type Of<'a, T: 'a>: 'a; )>::Of<'a, D>),
578		) -> Apply!(<Brand as Kind!( type Of<'a, T: 'a>: 'a; )>::Of<'a, E>) {
579			Brand::ref_lift2(
580				move |((a, b), c): &((A, B), C), d: &D| self(a, b, c, d),
581				&Brand::ref_lift2(
582					move |(a, b): &(A, B), c: &C| ((a.clone(), b.clone()), c.clone()),
583					&Brand::ref_lift2(|a: &A, b: &B| (a.clone(), b.clone()), fa, fb),
584					fc,
585				),
586				fd,
587			)
588		}
589	}
590
591	// -- Lift5Dispatch --
592
593	/// Trait that routes a lift5 operation to the appropriate type class method.
594	#[document_type_parameters(
595		"The lifetime.",
596		"The brand.",
597		"1st.",
598		"2nd.",
599		"3rd.",
600		"4th.",
601		"5th.",
602		"Result.",
603		"The first container type (owned or borrowed), inferred from the argument.",
604		"The second container type (owned or borrowed), inferred from the argument.",
605		"The third container type (owned or borrowed), inferred from the argument.",
606		"The fourth container type (owned or borrowed), inferred from the argument.",
607		"The fifth container type (owned or borrowed), inferred from the argument.",
608		"Dispatch marker."
609	)]
610	#[document_parameters("The closure implementing this dispatch.")]
611	pub trait Lift5Dispatch<
612		'a,
613		Brand: Kind_cdc7cd43dac7585f,
614		A: 'a,
615		B: 'a,
616		C: 'a,
617		D: 'a,
618		E: 'a,
619		G: 'a,
620		FA,
621		FB,
622		FC,
623		FD,
624		FE,
625		Marker,
626	> {
627		/// Perform the dispatched lift5 operation.
628		#[document_signature]
629		#[document_parameters("1st.", "2nd.", "3rd.", "4th.", "5th.")]
630		#[document_returns("Result context.")]
631		#[document_examples]
632		///
633		/// ```
634		/// use fp_library::{
635		/// 	brands::*,
636		/// 	functions::explicit::*,
637		/// };
638		/// let r = lift5::<OptionBrand, _, _, _, _, _, _, _, _, _, _, _, _>(
639		/// 	|a, b, c, d, e| a + b + c + d + e,
640		/// 	Some(1),
641		/// 	Some(2),
642		/// 	Some(3),
643		/// 	Some(4),
644		/// 	Some(5),
645		/// );
646		/// assert_eq!(r, Some(15));
647		/// ```
648		fn dispatch(
649			self,
650			fa: FA,
651			fb: FB,
652			fc: FC,
653			fd: FD,
654			fe: FE,
655		) -> Apply!(<Brand as Kind!( type Of<'a, T: 'a>: 'a; )>::Of<'a, G>);
656	}
657
658	/// Routes `Fn(A, B, C, D, E) -> G` closures through [`Lift::lift2`].
659	#[document_type_parameters(
660		"The lifetime.",
661		"The brand.",
662		"1st.",
663		"2nd.",
664		"3rd.",
665		"4th.",
666		"5th.",
667		"Result.",
668		"Closure."
669	)]
670	#[document_parameters("The closure that takes owned values.")]
671	impl<'a, Brand, A, B, C, D, E, G, Func>
672		Lift5Dispatch<
673			'a,
674			Brand,
675			A,
676			B,
677			C,
678			D,
679			E,
680			G,
681			Apply!(<Brand as Kind!( type Of<'a, T: 'a>: 'a; )>::Of<'a, A>),
682			Apply!(<Brand as Kind!( type Of<'a, T: 'a>: 'a; )>::Of<'a, B>),
683			Apply!(<Brand as Kind!( type Of<'a, T: 'a>: 'a; )>::Of<'a, C>),
684			Apply!(<Brand as Kind!( type Of<'a, T: 'a>: 'a; )>::Of<'a, D>),
685			Apply!(<Brand as Kind!( type Of<'a, T: 'a>: 'a; )>::Of<'a, E>),
686			Val,
687		> for Func
688	where
689		Brand: Lift,
690		A: Clone + 'a,
691		B: Clone + 'a,
692		C: Clone + 'a,
693		D: Clone + 'a,
694		E: Clone + 'a,
695		G: 'a,
696		Func: Fn(A, B, C, D, E) -> G + 'a,
697	{
698		#[document_signature]
699		#[document_parameters("1st.", "2nd.", "3rd.", "4th.", "5th.")]
700		#[document_returns("Result context.")]
701		#[document_examples]
702		///
703		/// ```
704		/// use fp_library::{
705		/// 	brands::*,
706		/// 	functions::explicit::*,
707		/// };
708		/// let r = lift5::<OptionBrand, _, _, _, _, _, _, _, _, _, _, _, _>(
709		/// 	|a, b, c, d, e| a + b + c + d + e,
710		/// 	Some(1),
711		/// 	Some(2),
712		/// 	Some(3),
713		/// 	Some(4),
714		/// 	Some(5),
715		/// );
716		/// assert_eq!(r, Some(15));
717		/// ```
718		fn dispatch(
719			self,
720			fa: Apply!(<Brand as Kind!( type Of<'a, T: 'a>: 'a; )>::Of<'a, A>),
721			fb: Apply!(<Brand as Kind!( type Of<'a, T: 'a>: 'a; )>::Of<'a, B>),
722			fc: Apply!(<Brand as Kind!( type Of<'a, T: 'a>: 'a; )>::Of<'a, C>),
723			fd: Apply!(<Brand as Kind!( type Of<'a, T: 'a>: 'a; )>::Of<'a, D>),
724			fe: Apply!(<Brand as Kind!( type Of<'a, T: 'a>: 'a; )>::Of<'a, E>),
725		) -> Apply!(<Brand as Kind!( type Of<'a, T: 'a>: 'a; )>::Of<'a, G>) {
726			Brand::lift2(
727				move |(((a, b), c), d), e| self(a, b, c, d, e),
728				Brand::lift2(
729					move |((a, b), c), d| (((a, b), c), d),
730					Brand::lift2(
731						move |(a, b), c| ((a, b), c),
732						Brand::lift2(|a, b| (a, b), fa, fb),
733						fc,
734					),
735					fd,
736				),
737				fe,
738			)
739		}
740	}
741
742	/// Routes `Fn(&A, &B, &C, &D, &E) -> G` closures through [`RefLift::ref_lift2`].
743	///
744	/// The containers must be passed by reference.
745	#[document_type_parameters(
746		"The lifetime.",
747		"The borrow lifetime.",
748		"The brand.",
749		"1st.",
750		"2nd.",
751		"3rd.",
752		"4th.",
753		"5th.",
754		"Result.",
755		"Closure."
756	)]
757	#[document_parameters("The closure that takes references.")]
758	impl<'a, 'b, Brand, A, B, C, D, E, G, Func>
759		Lift5Dispatch<
760			'a,
761			Brand,
762			A,
763			B,
764			C,
765			D,
766			E,
767			G,
768			&'b Apply!(<Brand as Kind!( type Of<'a, T: 'a>: 'a; )>::Of<'a, A>),
769			&'b Apply!(<Brand as Kind!( type Of<'a, T: 'a>: 'a; )>::Of<'a, B>),
770			&'b Apply!(<Brand as Kind!( type Of<'a, T: 'a>: 'a; )>::Of<'a, C>),
771			&'b Apply!(<Brand as Kind!( type Of<'a, T: 'a>: 'a; )>::Of<'a, D>),
772			&'b Apply!(<Brand as Kind!( type Of<'a, T: 'a>: 'a; )>::Of<'a, E>),
773			Ref,
774		> for Func
775	where
776		Brand: RefLift,
777		A: Clone + 'a,
778		B: Clone + 'a,
779		C: Clone + 'a,
780		D: Clone + 'a,
781		E: 'a,
782		G: 'a,
783		Func: Fn(&A, &B, &C, &D, &E) -> G + 'a,
784	{
785		#[document_signature]
786		#[document_parameters("1st.", "2nd.", "3rd.", "4th.", "5th.")]
787		#[document_returns("Result context.")]
788		#[document_examples]
789		///
790		/// ```
791		/// use fp_library::{
792		/// 	brands::*,
793		/// 	functions::explicit::*,
794		/// 	types::*,
795		/// };
796		/// let a = RcLazy::pure(1);
797		/// let b = RcLazy::pure(2);
798		/// let c = RcLazy::pure(3);
799		/// let d = RcLazy::pure(4);
800		/// let e = RcLazy::pure(5);
801		/// let r = lift5::<LazyBrand<RcLazyConfig>, _, _, _, _, _, _, _, _, _, _, _, _>(
802		/// 	|a: &i32, b: &i32, c: &i32, d: &i32, e: &i32| *a + *b + *c + *d + *e,
803		/// 	&a,
804		/// 	&b,
805		/// 	&c,
806		/// 	&d,
807		/// 	&e,
808		/// );
809		/// assert_eq!(*r.evaluate(), 15);
810		/// ```
811		fn dispatch(
812			self,
813			fa: &'b Apply!(<Brand as Kind!( type Of<'a, T: 'a>: 'a; )>::Of<'a, A>),
814			fb: &'b Apply!(<Brand as Kind!( type Of<'a, T: 'a>: 'a; )>::Of<'a, B>),
815			fc: &'b Apply!(<Brand as Kind!( type Of<'a, T: 'a>: 'a; )>::Of<'a, C>),
816			fd: &'b Apply!(<Brand as Kind!( type Of<'a, T: 'a>: 'a; )>::Of<'a, D>),
817			fe: &'b Apply!(<Brand as Kind!( type Of<'a, T: 'a>: 'a; )>::Of<'a, E>),
818		) -> Apply!(<Brand as Kind!( type Of<'a, T: 'a>: 'a; )>::Of<'a, G>) {
819			Brand::ref_lift2(
820				move |(((a, b), c), d): &(((A, B), C), D), e: &E| self(a, b, c, d, e),
821				&Brand::ref_lift2(
822					move |((a, b), c): &((A, B), C), d: &D| {
823						(((a.clone(), b.clone()), c.clone()), d.clone())
824					},
825					&Brand::ref_lift2(
826						move |(a, b): &(A, B), c: &C| ((a.clone(), b.clone()), c.clone()),
827						&Brand::ref_lift2(|a: &A, b: &B| (a.clone(), b.clone()), fa, fb),
828						fc,
829					),
830					fd,
831				),
832				fe,
833			)
834		}
835	}
836
837	// -- Inference wrappers --
838
839	/// Lifts a binary function into a functor context, inferring the brand
840	/// from the first container type.
841	///
842	/// The `Brand` type parameter is inferred from the concrete type of `fa`
843	/// via [`InferableBrand`](crate::kinds::InferableBrand_cdc7cd43dac7585f). The dispatch trait constrains `fb` to the same brand.
844	///
845	/// For types with multiple brands, use
846	/// [`explicit::lift2`](crate::functions::explicit::lift2) with a turbofish.
847	#[document_signature]
848	///
849	#[document_type_parameters(
850		"The lifetime of the values.",
851		"The first container type. Brand is inferred from this.",
852		"The second container type.",
853		"The type of the first value.",
854		"The type of the second value.",
855		"The type of the result.",
856		"Dispatch marker type, inferred automatically."
857	)]
858	///
859	#[document_parameters(
860		"The function to lift.",
861		"The first context (owned or borrowed).",
862		"The second context (owned or borrowed)."
863	)]
864	///
865	#[document_returns("A new context containing the result of applying the function.")]
866	#[document_examples]
867	///
868	/// ```
869	/// use fp_library::functions::*;
870	///
871	/// let z = lift2(|a, b| a + b, Some(1), Some(2));
872	/// assert_eq!(z, Some(3));
873	/// ```
874	pub fn lift2<'a, FA, FB, A: 'a, B: 'a, C: 'a, Marker>(
875		f: impl Lift2Dispatch<
876			'a,
877			<FA as InferableBrand_cdc7cd43dac7585f>::Brand,
878			A,
879			B,
880			C,
881			FA,
882			FB,
883			Marker,
884		>,
885		fa: FA,
886		fb: FB,
887	) -> Apply!(<<FA as InferableBrand!(type Of<'a, A: 'a>: 'a;)>::Brand as Kind!( type Of<'a, T: 'a>: 'a; )>::Of<'a, C>)
888	where
889		FA: InferableBrand_cdc7cd43dac7585f, {
890		f.dispatch(fa, fb)
891	}
892
893	/// Lifts a ternary function into a functor context, inferring the brand
894	/// from the first container type.
895	///
896	/// The `Brand` type parameter is inferred from the concrete type of `fa`
897	/// via [`InferableBrand`](crate::kinds::InferableBrand_cdc7cd43dac7585f). The dispatch trait constrains all other containers
898	/// to the same brand.
899	///
900	/// For types with multiple brands, use
901	/// [`explicit::lift3`](crate::functions::explicit::lift3) with a turbofish.
902	#[document_signature]
903	///
904	#[document_type_parameters(
905		"The lifetime of the values.",
906		"The first container type. Brand is inferred from this.",
907		"The second container type.",
908		"The third container type.",
909		"The type of the first value.",
910		"The type of the second value.",
911		"The type of the third value.",
912		"The type of the result.",
913		"Dispatch marker type, inferred automatically."
914	)]
915	///
916	#[document_parameters(
917		"The function to lift.",
918		"First context (owned or borrowed).",
919		"Second context (owned or borrowed).",
920		"Third context (owned or borrowed)."
921	)]
922	///
923	#[document_returns("A new context containing the result.")]
924	#[document_examples]
925	///
926	/// ```
927	/// use fp_library::functions::*;
928	///
929	/// let r = lift3(|a, b, c| a + b + c, Some(1), Some(2), Some(3));
930	/// assert_eq!(r, Some(6));
931	/// ```
932	pub fn lift3<'a, FA, FB, FC, A: 'a, B: 'a, C: 'a, D: 'a, Marker>(
933		f: impl Lift3Dispatch<
934			'a,
935			<FA as InferableBrand_cdc7cd43dac7585f>::Brand,
936			A,
937			B,
938			C,
939			D,
940			FA,
941			FB,
942			FC,
943			Marker,
944		>,
945		fa: FA,
946		fb: FB,
947		fc: FC,
948	) -> Apply!(<<FA as InferableBrand!(type Of<'a, A: 'a>: 'a;)>::Brand as Kind!( type Of<'a, T: 'a>: 'a; )>::Of<'a, D>)
949	where
950		FA: InferableBrand_cdc7cd43dac7585f, {
951		f.dispatch(fa, fb, fc)
952	}
953
954	/// Lifts a quaternary function into a functor context, inferring the brand
955	/// from the first container type.
956	///
957	/// The `Brand` type parameter is inferred from the concrete type of `fa`
958	/// via [`InferableBrand`](crate::kinds::InferableBrand_cdc7cd43dac7585f). The dispatch trait constrains all other containers
959	/// to the same brand.
960	///
961	/// For types with multiple brands, use
962	/// [`explicit::lift4`](crate::functions::explicit::lift4) with a turbofish.
963	#[document_signature]
964	///
965	#[document_type_parameters(
966		"The lifetime of the values.",
967		"The first container type. Brand is inferred from this.",
968		"The second container type.",
969		"The third container type.",
970		"The fourth container type.",
971		"The type of the first value.",
972		"The type of the second value.",
973		"The type of the third value.",
974		"The type of the fourth value.",
975		"The type of the result.",
976		"Dispatch marker type, inferred automatically."
977	)]
978	///
979	#[document_parameters(
980		"The function to lift.",
981		"First context (owned or borrowed).",
982		"Second context (owned or borrowed).",
983		"Third context (owned or borrowed).",
984		"Fourth context (owned or borrowed)."
985	)]
986	///
987	#[document_returns("A new context containing the result.")]
988	#[document_examples]
989	///
990	/// ```
991	/// use fp_library::functions::*;
992	///
993	/// let r = lift4(|a, b, c, d| a + b + c + d, Some(1), Some(2), Some(3), Some(4));
994	/// assert_eq!(r, Some(10));
995	/// ```
996	pub fn lift4<'a, FA, FB, FC, FD, A: 'a, B: 'a, C: 'a, D: 'a, E: 'a, Marker>(
997		f: impl Lift4Dispatch<
998			'a,
999			<FA as InferableBrand_cdc7cd43dac7585f>::Brand,
1000			A,
1001			B,
1002			C,
1003			D,
1004			E,
1005			FA,
1006			FB,
1007			FC,
1008			FD,
1009			Marker,
1010		>,
1011		fa: FA,
1012		fb: FB,
1013		fc: FC,
1014		fd: FD,
1015	) -> Apply!(<<FA as InferableBrand!(type Of<'a, A: 'a>: 'a;)>::Brand as Kind!( type Of<'a, T: 'a>: 'a; )>::Of<'a, E>)
1016	where
1017		FA: InferableBrand_cdc7cd43dac7585f, {
1018		f.dispatch(fa, fb, fc, fd)
1019	}
1020
1021	/// Lifts a quinary function into a functor context, inferring the brand
1022	/// from the first container type.
1023	///
1024	/// The `Brand` type parameter is inferred from the concrete type of `fa`
1025	/// via [`InferableBrand`](crate::kinds::InferableBrand_cdc7cd43dac7585f). The dispatch trait constrains all other containers
1026	/// to the same brand.
1027	///
1028	/// For types with multiple brands, use
1029	/// [`explicit::lift5`](crate::functions::explicit::lift5) with a turbofish.
1030	#[document_signature]
1031	///
1032	#[document_type_parameters(
1033		"The lifetime of the values.",
1034		"The first container type. Brand is inferred from this.",
1035		"The second container type.",
1036		"The third container type.",
1037		"The fourth container type.",
1038		"The fifth container type.",
1039		"The type of the first value.",
1040		"The type of the second value.",
1041		"The type of the third value.",
1042		"The type of the fourth value.",
1043		"The type of the fifth value.",
1044		"The type of the result.",
1045		"Dispatch marker type, inferred automatically."
1046	)]
1047	///
1048	#[document_parameters(
1049		"The function to lift.",
1050		"1st context (owned or borrowed).",
1051		"2nd context (owned or borrowed).",
1052		"3rd context (owned or borrowed).",
1053		"4th context (owned or borrowed).",
1054		"5th context (owned or borrowed)."
1055	)]
1056	///
1057	#[document_returns("A new context containing the result.")]
1058	#[document_examples]
1059	///
1060	/// ```
1061	/// use fp_library::functions::*;
1062	///
1063	/// let r = lift5(|a, b, c, d, e| a + b + c + d + e, Some(1), Some(2), Some(3), Some(4), Some(5));
1064	/// assert_eq!(r, Some(15));
1065	/// ```
1066	pub fn lift5<'a, FA, FB, FC, FD, FE, A: 'a, B: 'a, C: 'a, D: 'a, E: 'a, G: 'a, Marker>(
1067		f: impl Lift5Dispatch<
1068			'a,
1069			<FA as InferableBrand_cdc7cd43dac7585f>::Brand,
1070			A,
1071			B,
1072			C,
1073			D,
1074			E,
1075			G,
1076			FA,
1077			FB,
1078			FC,
1079			FD,
1080			FE,
1081			Marker,
1082		>,
1083		fa: FA,
1084		fb: FB,
1085		fc: FC,
1086		fd: FD,
1087		fe: FE,
1088	) -> Apply!(<<FA as InferableBrand!(type Of<'a, A: 'a>: 'a;)>::Brand as Kind!( type Of<'a, T: 'a>: 'a; )>::Of<'a, G>)
1089	where
1090		FA: InferableBrand_cdc7cd43dac7585f, {
1091		f.dispatch(fa, fb, fc, fd, fe)
1092	}
1093
1094	// -- Explicit dispatch free functions --
1095
1096	/// Explicit dispatch functions requiring a Brand turbofish.
1097	///
1098	/// For most use cases, prefer the inference-enabled wrappers from
1099	/// [`functions`](crate::functions).
1100	pub mod explicit {
1101		use super::*;
1102
1103		/// Lifts a binary function into a functor context.
1104		///
1105		/// Dispatches to either [`Lift::lift2`] or [`RefLift::ref_lift2`]
1106		/// based on the closure's argument types.
1107		///
1108		/// The `Marker`, `FA`, and `FB` type parameters are inferred automatically
1109		/// by the compiler from the closure's argument types and the container
1110		/// arguments.
1111		#[document_signature]
1112		///
1113		#[document_type_parameters(
1114			"The lifetime of the values.",
1115			"The brand of the context.",
1116			"The type of the first value.",
1117			"The type of the second value.",
1118			"The type of the result.",
1119			"The first container type (owned or borrowed), inferred from the argument.",
1120			"The second container type (owned or borrowed), inferred from the argument.",
1121			"Dispatch marker type, inferred automatically."
1122		)]
1123		///
1124		#[document_parameters(
1125			"The function to lift.",
1126			"The first context (owned for Val, borrowed for Ref).",
1127			"The second context (owned for Val, borrowed for Ref)."
1128		)]
1129		///
1130		#[document_returns("A new context containing the result of applying the function.")]
1131		#[document_examples]
1132		///
1133		/// ```
1134		/// use fp_library::{
1135		/// 	brands::*,
1136		/// 	functions::explicit::*,
1137		/// };
1138		/// let z = lift2::<OptionBrand, _, _, _, _, _, _>(|a, b| a + b, Some(1), Some(2));
1139		/// assert_eq!(z, Some(3));
1140		/// ```
1141		pub fn lift2<'a, Brand: Kind_cdc7cd43dac7585f, A: 'a, B: 'a, C: 'a, FA, FB, Marker>(
1142			f: impl Lift2Dispatch<'a, Brand, A, B, C, FA, FB, Marker>,
1143			fa: FA,
1144			fb: FB,
1145		) -> Apply!(<Brand as Kind!( type Of<'a, T: 'a>: 'a; )>::Of<'a, C>) {
1146			f.dispatch(fa, fb)
1147		}
1148
1149		/// Lifts a ternary function into a functor context.
1150		///
1151		/// Dispatches to [`Lift::lift2`] or [`RefLift::ref_lift2`] based on the closure's argument types.
1152		///
1153		/// When dispatched through the Ref path (`Fn(&A, &B, &C) -> D`), the intermediate
1154		/// types `A` and `B` must implement [`Clone`] because the implementation builds
1155		/// the ternary lift from nested binary `ref_lift2` calls, which requires
1156		/// constructing intermediate tuples.
1157		#[document_signature]
1158		#[document_type_parameters(
1159			"The lifetime.",
1160			"The brand.",
1161			"First type.",
1162			"Second type.",
1163			"Third type.",
1164			"Result type.",
1165			"The first container type (owned or borrowed), inferred from the argument.",
1166			"The second container type (owned or borrowed), inferred from the argument.",
1167			"The third container type (owned or borrowed), inferred from the argument.",
1168			"Dispatch marker."
1169		)]
1170		#[document_parameters(
1171			"The function to lift.",
1172			"First context (owned for Val, borrowed for Ref).",
1173			"Second context (owned for Val, borrowed for Ref).",
1174			"Third context (owned for Val, borrowed for Ref)."
1175		)]
1176		#[document_returns("A new context containing the result.")]
1177		#[document_examples]
1178		///
1179		/// ```
1180		/// use fp_library::{
1181		/// 	brands::*,
1182		/// 	functions::explicit::*,
1183		/// };
1184		/// let r = lift3::<OptionBrand, _, _, _, _, _, _, _, _>(
1185		/// 	|a, b, c| a + b + c,
1186		/// 	Some(1),
1187		/// 	Some(2),
1188		/// 	Some(3),
1189		/// );
1190		/// assert_eq!(r, Some(6));
1191		/// ```
1192		pub fn lift3<
1193			'a,
1194			Brand: Kind_cdc7cd43dac7585f,
1195			A: 'a,
1196			B: 'a,
1197			C: 'a,
1198			D: 'a,
1199			FA,
1200			FB,
1201			FC,
1202			Marker,
1203		>(
1204			f: impl Lift3Dispatch<'a, Brand, A, B, C, D, FA, FB, FC, Marker>,
1205			fa: FA,
1206			fb: FB,
1207			fc: FC,
1208		) -> Apply!(<Brand as Kind!( type Of<'a, T: 'a>: 'a; )>::Of<'a, D>) {
1209			f.dispatch(fa, fb, fc)
1210		}
1211
1212		/// Lifts a quaternary function into a functor context.
1213		///
1214		/// When dispatched through the Ref path (`Fn(&A, &B, &C, &D) -> E`), the
1215		/// intermediate types `A`, `B`, and `C` must implement [`Clone`] because
1216		/// the implementation builds the quaternary lift from nested binary
1217		/// `ref_lift2` calls, which requires constructing intermediate tuples.
1218		#[document_signature]
1219		#[document_type_parameters(
1220			"The lifetime.",
1221			"The brand.",
1222			"First.",
1223			"Second.",
1224			"Third.",
1225			"Fourth.",
1226			"Result.",
1227			"The first container type (owned or borrowed), inferred from the argument.",
1228			"The second container type (owned or borrowed), inferred from the argument.",
1229			"The third container type (owned or borrowed), inferred from the argument.",
1230			"The fourth container type (owned or borrowed), inferred from the argument.",
1231			"Dispatch marker."
1232		)]
1233		#[document_parameters(
1234			"The function to lift.",
1235			"First (owned for Val, borrowed for Ref).",
1236			"Second (owned for Val, borrowed for Ref).",
1237			"Third (owned for Val, borrowed for Ref).",
1238			"Fourth (owned for Val, borrowed for Ref)."
1239		)]
1240		#[document_returns("Result context.")]
1241		#[document_examples]
1242		///
1243		/// ```
1244		/// use fp_library::{
1245		/// 	brands::*,
1246		/// 	functions::explicit::*,
1247		/// };
1248		/// let r = lift4::<OptionBrand, _, _, _, _, _, _, _, _, _, _>(
1249		/// 	|a, b, c, d| a + b + c + d,
1250		/// 	Some(1),
1251		/// 	Some(2),
1252		/// 	Some(3),
1253		/// 	Some(4),
1254		/// );
1255		/// assert_eq!(r, Some(10));
1256		/// ```
1257		pub fn lift4<
1258			'a,
1259			Brand: Kind_cdc7cd43dac7585f,
1260			A: 'a,
1261			B: 'a,
1262			C: 'a,
1263			D: 'a,
1264			E: 'a,
1265			FA,
1266			FB,
1267			FC,
1268			FD,
1269			Marker,
1270		>(
1271			f: impl Lift4Dispatch<'a, Brand, A, B, C, D, E, FA, FB, FC, FD, Marker>,
1272			fa: FA,
1273			fb: FB,
1274			fc: FC,
1275			fd: FD,
1276		) -> Apply!(<Brand as Kind!( type Of<'a, T: 'a>: 'a; )>::Of<'a, E>) {
1277			f.dispatch(fa, fb, fc, fd)
1278		}
1279
1280		/// Lifts a quinary function into a functor context.
1281		///
1282		/// When dispatched through the Ref path (`Fn(&A, &B, &C, &D, &E) -> G`),
1283		/// the intermediate types `A`, `B`, `C`, and `D` must implement [`Clone`]
1284		/// because the implementation builds the quinary lift from nested binary
1285		/// `ref_lift2` calls, which requires constructing intermediate tuples.
1286		#[document_signature]
1287		#[document_type_parameters(
1288			"The lifetime.",
1289			"The brand.",
1290			"1st.",
1291			"2nd.",
1292			"3rd.",
1293			"4th.",
1294			"5th.",
1295			"Result.",
1296			"The first container type (owned or borrowed), inferred from the argument.",
1297			"The second container type (owned or borrowed), inferred from the argument.",
1298			"The third container type (owned or borrowed), inferred from the argument.",
1299			"The fourth container type (owned or borrowed), inferred from the argument.",
1300			"The fifth container type (owned or borrowed), inferred from the argument.",
1301			"Dispatch marker."
1302		)]
1303		#[document_parameters(
1304			"The function to lift.",
1305			"1st (owned for Val, borrowed for Ref).",
1306			"2nd (owned for Val, borrowed for Ref).",
1307			"3rd (owned for Val, borrowed for Ref).",
1308			"4th (owned for Val, borrowed for Ref).",
1309			"5th (owned for Val, borrowed for Ref)."
1310		)]
1311		#[document_returns("Result context.")]
1312		#[document_examples]
1313		///
1314		/// ```
1315		/// use fp_library::{
1316		/// 	brands::*,
1317		/// 	functions::explicit::*,
1318		/// };
1319		/// let r = lift5::<OptionBrand, _, _, _, _, _, _, _, _, _, _, _, _>(
1320		/// 	|a, b, c, d, e| a + b + c + d + e,
1321		/// 	Some(1),
1322		/// 	Some(2),
1323		/// 	Some(3),
1324		/// 	Some(4),
1325		/// 	Some(5),
1326		/// );
1327		/// assert_eq!(r, Some(15));
1328		/// ```
1329		pub fn lift5<
1330			'a,
1331			Brand: Kind_cdc7cd43dac7585f,
1332			A: 'a,
1333			B: 'a,
1334			C: 'a,
1335			D: 'a,
1336			E: 'a,
1337			G: 'a,
1338			FA,
1339			FB,
1340			FC,
1341			FD,
1342			FE,
1343			Marker,
1344		>(
1345			f: impl Lift5Dispatch<'a, Brand, A, B, C, D, E, G, FA, FB, FC, FD, FE, Marker>,
1346			fa: FA,
1347			fb: FB,
1348			fc: FC,
1349			fd: FD,
1350			fe: FE,
1351		) -> Apply!(<Brand as Kind!( type Of<'a, T: 'a>: 'a; )>::Of<'a, G>) {
1352			f.dispatch(fa, fb, fc, fd, fe)
1353		}
1354	}
1355}
1356
1357pub use inner::*;