pub fn mean(data: &Vec<i16>) -> Option<i16> {
let sum = data.iter().map(|&b| b as i64).sum::<i64>() as i16;
let count = data.len() as i16;
match count {
positive if positive > 0 => Some(sum / count),
_ => None,
}
}
pub fn mean_float(data: &Vec<f32>) -> Option<f32> {
let sum = data.iter().map(|&b| b as f64).sum::<f64>() as f32;
let count = data.len() as f32;
match count {
positive if positive > 0.0 => Some(sum / count),
_ => None,
}
}
pub fn variance(data: &Vec<i16>) -> Option<f32> {
match (mean(data), data.len()) {
(Some(d_mean), count) if count > 0 => Some(
data.iter()
.map(|val| {
let diff = d_mean - (*val);
diff as f32 * diff as f32
})
.sum::<f32>()
/ count as f32,
),
_ => None,
}
}
pub fn zero_mean_variance_float(data: &Vec<f32>) -> Option<f32> {
if data.len() > 0 {
return Some(
data.iter()
.map(|val| {
let diff = *val;
diff * diff
})
.sum::<f32>()
/ data.len() as f32,
);
} else {
None
}
}
pub fn next_lower_power_two(size: usize) -> usize {
let mut two_to_n: usize = 2;
loop {
let temp: usize = two_to_n * 2;
if temp > size {
break;
}
two_to_n = temp;
}
two_to_n
}
pub fn next_upper_power_two(size: usize) -> usize {
let mut two_to_n: usize = 2;
loop {
let temp: usize = two_to_n * 2;
two_to_n = temp;
if temp >= size {
break;
}
}
two_to_n
}
pub fn zero_mean_variance(data: &Vec<i16>) -> Option<f32> {
if data.len() > 0 {
return Some(
data.iter()
.map(|val| {
let diff = *val;
diff as f32 * diff as f32
})
.sum::<f32>()
/ data.len() as f32,
);
} else {
None
}
}
pub fn std_deviation_float(data: &Vec<f32>) -> Option<f32> {
match (mean_float(data), data.len()) {
(Some(_mean), count) if count > 0 => {
let var = data
.iter()
.map(|val| {
let diff = _mean - (*val);
diff * diff
})
.sum::<f32>()
/ count as f32;
Some(var.sqrt())
}
_ => None,
}
}
pub fn std_deviation(data: &Vec<i16>) -> Option<f32> {
match (mean(data), data.len()) {
(Some(_mean), count) if count > 0 => {
let var = data
.iter()
.map(|val| {
let diff = _mean - (*val);
diff as f32 * diff as f32
})
.sum::<f32>()
/ count as f32;
Some(var.sqrt())
}
_ => None,
}
}
#[cfg(test)]
mod test {
use super::*;
#[test]
fn test_mean() {
let vec = vec![0, 1, 2, 4, 5, 6];
assert_eq!(mean(&vec).unwrap(), 3);
}
#[test]
fn test_mean_big() {
let vec = vec![i16::MIN, i16::MIN, i16::MAX, i16::MAX];
assert_eq!(mean(&vec).unwrap(), 0);
}
#[test]
fn test_variance() {
let vec = vec![66, 30, 40, 64];
let res = variance(&vec).unwrap();
assert_eq!(res, 238.0);
let vec2 = vec![51, 21, 79, 49];
let res2 = variance(&vec2).unwrap();
assert_eq!(res2, 421.0);
}
#[test]
fn test_zero_mean_variance() {
let vec = vec![66, 30, 40, 64];
let res = zero_mean_variance(&vec).unwrap();
assert_eq!(res, 2738.0);
let vec2 = vec![51, 21, 79, 49];
let res2 = zero_mean_variance(&vec2).unwrap();
assert_eq!(res2, 2921.0);
}
#[test]
fn test_std_deviation() {
let vec = vec![66, 30, 40, 64];
println!("{:?}", std_deviation(&vec).unwrap());
let res = format!("{:.2}", std_deviation(&vec).unwrap());
assert_eq!(res, "15.43");
let vec2 = vec![51, 21, 79, 49];
println!("{:?}", std_deviation(&vec2).unwrap());
let res2 = format!("{:.2}", std_deviation(&vec2).unwrap());
assert_eq!(res2, "20.52"); }
}