pub use crate::traits::{Configurable, Plotable, Saveable};
use core::ops::Add;
use average::Variance;
pub mod comparison;
pub use comparison::SequenceErrors;
#[derive(Debug, PartialEq, Clone)]
#[cfg_attr(feature = "use-serde", derive(serde::Serialize, serde::Deserialize))]
pub struct SequenceError {
data: Vec<(f64, f64)>,
config: crate::configuration::Configuration,
}
impl SequenceError {
pub fn new<I, J, T>(data: I) -> SequenceError
where
I: IntoIterator<Item = J>,
J: IntoIterator<Item = T>,
T: Into<f64>,
{
let data: Vec<(f64, f64)> = data
.into_iter()
.map(|j| {
let v: Variance = j.into_iter().map(|t| t.into()).collect();
(v.mean(), v.error())
})
.collect();
let config = crate::configuration::Configuration::default();
SequenceError { data, config }
}
}
impl Add for SequenceError {
type Output = crate::SequenceErrors;
fn add(self, other: crate::SequenceError) -> crate::SequenceErrors {
let mut cmp = self.into();
cmp += other;
cmp
}
}
impl Configurable for SequenceError {
fn configuration_mut(&mut self) -> &mut crate::configuration::Configuration {
&mut self.config
}
fn configuration(&self) -> &crate::configuration::Configuration {
&self.config
}
}
impl Saveable for SequenceError {
fn plotable_data(&self) -> String {
if self.data.is_empty() {
eprintln!("Warning: There is no data.");
}
let mut plotable_data = String::new();
for (counter, (value, error)) in self.data.clone().into_iter().enumerate() {
plotable_data.push_str(&format!("{}\t{}\t{}\n", counter, value, error));
}
plotable_data
}
}
impl Plotable for SequenceError {
fn plot_script(&self) -> String {
let mut gnuplot_script = self.opening_plot_script();
let dashtype = self.dashtype().unwrap_or(1);
gnuplot_script += &format!(
"plot {:?} using 1:2 with {} dashtype {}, \"\" using 1:2:3 with yerrorbars \n",
self.data_path(),
self.style(),
dashtype,
);
gnuplot_script += &self.ending_plot_script();
gnuplot_script
}
}
impl<T> From<crate::Densities<T>> for SequenceError
where
T: Into<f64> + core::fmt::Display + Clone,
{
fn from(mut densities: crate::Densities<T>) -> Self {
let data: Vec<Vec<f64>> = (0..densities.data_set.len())
.map(|i| {
densities.data_set[i]
.realizations
.iter()
.map(|t| t.clone().into())
.collect()
})
.collect();
let mut seq_err = SequenceError::new(data);
let config = seq_err.configuration_mut();
*config = densities.configuration_mut().clone();
seq_err
}
}
#[cfg(test)]
mod tests {
use super::*;
#[test]
fn set_style() {
let data = vec![vec![0., 1.], vec![0., 1., 2.], vec![3., 4., 5.]];
let mut seq = SequenceError::new(data);
seq.set_style("points").unwrap();
assert_eq!(
&crate::configuration::plot::style::Style::Points,
seq.style()
);
}
#[test]
fn from_densitites() {
use crate::prelude::*;
let many_dens = (0..5).map(|_| pre::Density::new(0..10));
let mut densities: pre::Densities<u32> = pre::Densities::new(many_dens);
densities.set_title("My title");
let seq_err = pre::SequenceError::from(densities.clone());
assert_eq!(seq_err.title(), densities.title());
}
}