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
use std::cmp::Ordering::Equal;
use std::collections::HashMap;
#[derive(Debug)]
pub enum Metric {
Median,
Average,
}
pub fn calculate_ranking(
all_rankings: Vec<(&str, Vec<&str>)>,
metric: Metric,
) -> Vec<(f32, String)> {
let mut rank_options: HashMap<String, Vec<usize>> = HashMap::new();
for label_and_scores in all_rankings {
let mut counter = 0;
let (_label, score) = label_and_scores;
for s in score {
rank_options
.entry(String::from(s))
.or_insert_with(Vec::new)
.push(counter);
counter = counter + 1;
}
}
let mut results: Vec<(f32, String)> = vec![];
match metric {
Metric::Median => {
println!("Ranking Metric: {}", "Median");
for (k, v) in rank_options.iter() {
results.push((median(v), String::from(k)));
}
}
Metric::Average => {
println!("Ranking Metric: {}", "Average");
for (k, v) in rank_options.iter() {
results.push((average(v), String::from(k)));
}
}
}
results.sort_by(|a, b| a.partial_cmp(b).unwrap_or(Equal));
results
}
fn average(imm_numbers: &Vec<usize>) -> f32 {
let numbers = imm_numbers
.into_iter()
.map(|i| *i as i32)
.collect::<Vec<i32>>();
numbers.iter().sum::<i32>() as f32 / numbers.len() as f32
}
fn median(imm_numbers: &Vec<usize>) -> f32 {
let mut numbers = imm_numbers.to_vec();
numbers.sort();
let mid = numbers.len() / 2;
numbers[mid] as f32
}