Skip to main content

fp_library/types/
first.rs

1//! A newtype wrapper whose [`Semigroup`](crate::classes::Semigroup) instance always keeps the first
2//! (leftmost) value.
3//!
4//! ### Examples
5//!
6//! ```
7//! use fp_library::{
8//! 	functions::*,
9//! 	types::First,
10//! };
11//!
12//! assert_eq!(append(First(1), First(2)), First(1));
13//! ```
14
15#[fp_macros::document_module]
16mod inner {
17	use {
18		crate::classes::*,
19		fp_macros::*,
20	};
21
22	/// A newtype wrapper whose [`Semigroup`] instance always keeps the first value.
23	///
24	/// `append(First(a), First(b))` returns `First(a)`, discarding `b`.
25	///
26	/// There is no [`Monoid`] instance because there is no identity element.
27	#[document_examples]
28	///
29	/// ```
30	/// use fp_library::{
31	/// 	functions::*,
32	/// 	types::First,
33	/// };
34	///
35	/// assert_eq!(append(First("hello"), First("world")), First("hello"));
36	/// ```
37	#[cfg_attr(feature = "serde", derive(serde::Serialize, serde::Deserialize))]
38	#[derive(Clone, Copy, Debug, Default, Eq, Hash, Ord, PartialEq, PartialOrd)]
39	pub struct First<A>(
40		/// The wrapped value.
41		pub A,
42	);
43
44	#[document_type_parameters("The wrapped type.")]
45	impl<A> Semigroup for First<A> {
46		/// Returns the first (leftmost) value, discarding the second.
47		#[document_signature]
48		///
49		#[document_parameters("The first value (kept).", "The second value (discarded).")]
50		///
51		#[document_returns("The first value.")]
52		#[document_examples]
53		///
54		/// ```
55		/// use fp_library::{
56		/// 	functions::*,
57		/// 	types::First,
58		/// };
59		///
60		/// assert_eq!(append(First(1), First(2)), First(1));
61		/// ```
62		fn append(
63			a: Self,
64			_b: Self,
65		) -> Self {
66			a
67		}
68	}
69}
70
71pub use inner::*;
72
73#[cfg(test)]
74mod tests {
75	use {
76		super::*,
77		crate::functions::*,
78		quickcheck_macros::quickcheck,
79	};
80
81	#[quickcheck]
82	fn semigroup_associativity(
83		a: i32,
84		b: i32,
85		c: i32,
86	) -> bool {
87		let x = First(a);
88		let y = First(b);
89		let z = First(c);
90		append(x, append(y, z)) == append(append(x, y), z)
91	}
92}