1#![crate_name = "editdistancewf"]
2#![crate_type = "lib"]
3
4fn materialise<T, I: Iterator<Item=T>>(iter: I) -> Vec<T> {
5 let mut dest = Vec::new();
6 dest.extend(iter);
7
8 dest
9}
10
11pub fn distance<T, I: Iterator<Item=T>>(left_stream: I, right_stream: I) -> usize
12 where T: Eq {
13 let left = materialise(left_stream);
14 let right = materialise(right_stream);
15
16 let width = left.len() + 1;
17 let depth = right.len() + 1;
18
19 let mut current = vec![0; width];
20 let mut previous = vec![0; width];
21
22 for i in 0..width {
23 previous[i] = i;
24 }
25
26 current[0] = previous[0] + 1;
27
28 for row in 1..depth {
29 for column in 1..width {
30 if left[column - 1] == right[row - 1] {
31 current[column] = previous[column - 1];
32 } else {
33 let above = previous[column] + 1;
34 let diag = previous[column - 1] + 1;
35 let aside = current [column - 1] + 1;
36
37 current[column] = *[above, diag, aside]
38 .iter()
39 .min()
40 .unwrap();
41 }
42 }
43
44 previous = current.clone();
45 current = vec![0; width];
46 current[0] = row+1;
47 }
48
49 previous[width-1]
50 }