1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
pub mod vector {
pub fn init<T>(capacity: usize, f: fn(usize) -> T) -> Vec<T> {
let mut v = Vec::with_capacity(capacity);
for i in 0..capacity {
v.push(f(i));
}
v
}
pub fn zip_with<T, U, V>(mut first: Vec<T>, mut second: Vec<U>, with: fn(T, U) -> V) -> Vec<V> {
if first.len() != second.len() {
panic!("You need to have equal lists");
}
let length = first.len();
let mut v = Vec::with_capacity(length);
for _ in 0..length {
let x = first.drain(0..1).next().unwrap();
let y = second.drain(0..1).next().unwrap();
v.push(with(x, y));
}
v
}
pub fn zip<T, U>(first: Vec<T>, second: Vec<U>) -> Vec<(T, U)> {
zip_with(first, second, |x, y| (x, y))
}
}
pub mod truth {
pub fn all<'a, T>(elems: &'a Vec<T>, f: fn(&'a T) -> bool) -> bool {
elems.iter().fold(true, |acc, x| acc && f(x))
}
pub fn any<'a, T>(elems: &'a Vec<T>, f: fn(&'a T) -> bool) -> bool {
elems.iter().fold(false, |acc, x| acc || f(x))
}
}
pub mod futures {
#[macro_export]
macro_rules! pipe {
($init:tt $(=>$fn:ident)+) => {{
let mut r = $init;
$( r = $fn(r).await; )*
r
}}
}
}
#[cfg(test)]
mod tests {
use super::*;
#[test]
fn test_vec_init() {
let v = vector::init(4, |x| x.pow(2));
assert_eq!(v[0], 0);
assert_eq!(v[1], 1);
assert_eq!(v[2], 4);
assert_eq!(v[3], 9);
println!("{:?}", v);
}
#[test]
fn test_zip_with() {
let xs = vec![1, 2, 3];
let ys = vec![4, 5, 6];
assert_eq!(vector::zip_with(xs, ys, |x, y| x + y), vec![5, 7, 9]);
}
#[test]
fn test_zip() {
let xs = vec![1, 2, 3];
let ys = vec![4, 5, 6];
let zs = vector::zip(xs, ys);
println!("{:?}", zs);
assert_eq!(zs[0], (1, 4));
assert_eq!(zs[1], (2, 5));
assert_eq!(zs[2], (3, 6));
}
#[test]
fn test_all() {
let xs = vec![1, 3, 5, 7, 9];
let is_odd = |x| x % 2 != 0;
assert_eq!(truth::all(&xs, is_odd), true)
}
#[test]
fn test_any() {
let xs = vec![1, 4, 5, 7, 9];
let is_even = |x| x % 2 == 0;
assert_eq!(truth::any(&xs, is_even), true)
}
async fn double(x: i32) -> i32 {
x + x
}
async fn square(x: i32) -> i32 {
x * x
}
#[tokio::test]
async fn test_piping() {
let x = pipe!(2
=> double
=> square
=> double
=> square);
assert_eq!(x, 1024);
}
}