pub trait Sequence<T> {
fn count(&self) -> usize;
fn map(&self, f: &dyn Fn(&T) -> T) -> Self;
fn map_with(&self, other: &Self, f: &dyn Fn(&T, &T) -> T) -> Self;
fn all(&self, f: &dyn Fn(&T) -> bool) -> bool;
fn all_with(&self, other: &Self, f: &dyn Fn(&T, &T) -> bool) -> bool;
fn any(&self, f: &dyn Fn(&T) -> bool) -> bool;
fn any_with(&self, other: &Self, f: &dyn Fn(&T, &T) -> bool) -> bool;
}
impl<T> Sequence<T> for () {
fn count(&self) -> usize {
0
}
fn map(&self, _f: &dyn Fn(&T) -> T) -> Self {
()
}
fn map_with(&self, _xs: &Self, _f: &dyn Fn(&T, &T) -> T) -> Self {
()
}
fn all(&self, _f: &dyn Fn(&T) -> bool) -> bool {
true
}
fn all_with(&self, _other: &Self, _f: &dyn Fn(&T, &T) -> bool) -> bool {
true
}
fn any(&self, _f: &dyn Fn(&T) -> bool) -> bool {
true
}
fn any_with(&self, _other: &Self, _f: &dyn Fn(&T, &T) -> bool) -> bool {
true
}
}
impl<T> Sequence<T> for (T,) {
fn count(&self) -> usize {
1
}
fn map(&self, f: &dyn Fn(&T) -> T) -> Self {
(f(&self.0),)
}
fn map_with(&self, xs: &Self, f: &dyn Fn(&T, &T) -> T) -> Self {
(f(&self.0, &xs.0),)
}
fn all(&self, f: &dyn Fn(&T) -> bool) -> bool {
f(&self.0)
}
fn all_with(&self, other: &Self, f: &dyn Fn(&T, &T) -> bool) -> bool {
f(&self.0, &other.0)
}
fn any(&self, f: &dyn Fn(&T) -> bool) -> bool {
f(&self.0)
}
fn any_with(&self, other: &Self, f: &dyn Fn(&T, &T) -> bool) -> bool {
f(&self.0, &other.0)
}
}
impl<T> Sequence<T> for (T, T) {
fn count(&self) -> usize {
2
}
fn map(&self, f: &dyn Fn(&T) -> T) -> Self {
(f(&self.0), f(&self.1))
}
fn map_with(&self, xs: &Self, f: &dyn Fn(&T, &T) -> T) -> Self {
(f(&self.0, &xs.0), f(&self.1, &xs.1))
}
fn all(&self, f: &dyn Fn(&T) -> bool) -> bool {
f(&self.0) && f(&self.1)
}
fn all_with(&self, other: &Self, f: &dyn Fn(&T, &T) -> bool) -> bool {
f(&self.0, &other.0) && f(&self.1, &other.1)
}
fn any(&self, f: &dyn Fn(&T) -> bool) -> bool {
f(&self.0) || f(&self.1)
}
fn any_with(&self, other: &Self, f: &dyn Fn(&T, &T) -> bool) -> bool {
f(&self.0, &other.0) || f(&self.1, &other.1)
}
}
impl<T> Sequence<T> for (T, T, T) {
fn count(&self) -> usize {
3
}
fn map(&self, f: &dyn Fn(&T) -> T) -> Self {
(f(&self.0), f(&self.1), f(&self.2))
}
fn map_with(&self, xs: &Self, f: &dyn Fn(&T, &T) -> T) -> Self {
(f(&self.0, &xs.0), f(&self.1, &xs.1), f(&self.2, &xs.2))
}
fn all(&self, f: &dyn Fn(&T) -> bool) -> bool {
f(&self.0) && f(&self.1) && f(&self.2)
}
fn all_with(&self, other: &Self, f: &dyn Fn(&T, &T) -> bool) -> bool {
let (x, y) = (self, other);
f(&x.0, &y.0) && f(&x.1, &y.1) && f(&x.2, &y.2)
}
fn any(&self, f: &dyn Fn(&T) -> bool) -> bool {
f(&self.0) || f(&self.1) || f(&self.2)
}
fn any_with(&self, other: &Self, f: &dyn Fn(&T, &T) -> bool) -> bool {
let (x, y) = (self, other);
f(&x.0, &y.0) || f(&x.1, &y.1) || f(&x.2, &y.2)
}
}
impl<T> Sequence<T> for (T, T, T, T) {
fn count(&self) -> usize {
4
}
fn map(&self, f: &dyn Fn(&T) -> T) -> Self {
(f(&self.0), f(&self.1), f(&self.2), f(&self.3))
}
fn map_with(&self, other: &Self, f: &dyn Fn(&T, &T) -> T) -> Self {
let (x, y) = (self, other);
(f(&x.0, &y.0), f(&x.1, &y.1), f(&x.2, &y.2), f(&x.3, &y.3))
}
fn all(&self, f: &dyn Fn(&T) -> bool) -> bool {
f(&self.0) && f(&self.1) && f(&self.2) && f(&self.3)
}
fn all_with(&self, other: &Self, f: &dyn Fn(&T, &T) -> bool) -> bool {
let (x, y) = (self, other);
f(&x.0, &y.0) && f(&x.1, &y.1) && f(&x.2, &y.2) && f(&x.3, &y.3)
}
fn any(&self, f: &dyn Fn(&T) -> bool) -> bool {
f(&self.0) || f(&self.1) || f(&self.2) || f(&self.3)
}
fn any_with(&self, other: &Self, f: &dyn Fn(&T, &T) -> bool) -> bool {
let (x, y) = (self, other);
f(&x.0, &y.0) || f(&x.1, &y.1) || f(&x.2, &y.2) || f(&x.3, &y.3)
}
}
macro_rules! array_sequence {
($size:expr) => {
impl<T: Copy> Sequence<T> for [T; $size] {
fn count(&self) -> usize {
$size
}
fn map(&self, f: &dyn Fn(&T) -> T) -> Self {
let mut result: [T; $size] = *self;
for (i, x) in self.iter().enumerate() {
result[i] = f(x);
}
result
}
fn map_with(&self, other: &Self, f: &dyn Fn(&T, &T) -> T) -> Self {
let mut result: [T; $size] = *self;
for (i, xs) in self.iter().zip(other).enumerate() {
result[i] = f(xs.0, xs.1);
}
result
}
fn all(&self, f: &dyn Fn(&T) -> bool) -> bool {
self.into_iter().all(f)
}
fn all_with(&self, other: &Self, f: &dyn Fn(&T, &T) -> bool) -> bool {
self.into_iter().zip(other).all(|(x, y)| f(x, y))
}
fn any(&self, f: &dyn Fn(&T) -> bool) -> bool {
self.into_iter().any(f)
}
fn any_with(&self, other: &Self, f: &dyn Fn(&T, &T) -> bool) -> bool {
self.into_iter().zip(other).any(|(x, y)| f(x, y))
}
}
};
($size:expr, $($others:expr),+) => {
array_sequence! {$size}
array_sequence! {$($others),+}
};
}
array_sequence! {
0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, 16
}