use std::cmp::Ordering;
use node_defs::{Container, NodeData, Sum, Product, Power, Primitive};
#[derive(Eq, Ord, PartialEq, PartialOrd)]
enum PrimitiveType {
Input,
SystemVariable,
Parameter,
Sigmoid,
}
impl<T: NodeData> Primitive<T> {
fn simplify(&self) -> PrimitiveType {
match self {
&Primitive::Input(_) => PrimitiveType::Input,
&Primitive::SystemVariable(_) => PrimitiveType::SystemVariable,
&Primitive::Parameter(_) => PrimitiveType::Parameter,
&Primitive::Sigmoid(_, _) => PrimitiveType::Sigmoid,
}
}
}
impl<T: NodeData> Ord for Sum<T> {
fn cmp(&self, other: &Sum<T>) -> Ordering {
let cmp_result = self.constant.cmp(&other.constant);
match cmp_result {
Ordering::Equal => {
for (self_term, other_term) in
self.terms
.clone()
.into_iter()
.zip(other.terms.clone()) {
let cmp_result = self_term.cmp(&other_term);
match cmp_result {
Ordering::Equal => (),
_ => return cmp_result,
}
}
let cmp_result = self.terms.len().cmp(&other.terms.len());
match cmp_result {
Ordering::Equal => self.minus.cmp(&other.minus),
_ => cmp_result,
}
}
_ => cmp_result,
}
}
}
impl<T: NodeData> Ord for Product<T> {
fn cmp(&self, other: &Product<T>) -> Ordering {
let cmp_result = self.fuzzy_cmp(other);
match cmp_result {
Ordering::Equal => self.coefficient.cmp(&other.coefficient),
_ => cmp_result,
}
}
}
impl<T: NodeData> Product<T> {
pub fn fuzzy_cmp(&self, other: &Product<T>) -> Ordering {
for (self_power, other_power) in
self.powers
.clone()
.into_iter()
.zip(other.powers.clone()) {
let cmp_result = self_power.cmp(&other_power);
match cmp_result {
Ordering::Equal => (),
_ => return cmp_result,
}
}
self.powers.len().cmp(&other.powers.len())
}
}
impl<T: NodeData> Ord for Power<T> {
fn cmp(&self, other: &Power<T>) -> Ordering {
match self.fuzzy_cmp(&other) {
Ordering::Equal => self.exponent.cmp(&other.exponent),
cmp_result => cmp_result,
}
}
}
impl<T: NodeData> Power<T> {
pub fn fuzzy_cmp(&self, other: &Power<T>) -> Ordering {
self.primitive.cmp(&other.primitive)
}
}
impl<T: NodeData> Ord for Primitive<T> {
fn cmp(&self, other: &Primitive<T>) -> Ordering {
match (self, other) {
(&Primitive::Input(ref a), &Primitive::Input(ref b)) => a.cmp(b),
(&Primitive::SystemVariable(ref a), &Primitive::SystemVariable(ref b)) => a.cmp(b),
(&Primitive::Parameter(ref a), &Primitive::Parameter(ref b)) => a.cmp(b),
(&Primitive::Sigmoid(minus_a, ref a), &Primitive::Sigmoid(minus_b, ref b)) => {
let cmp_result = a.cmp(b);
match cmp_result {
Ordering::Equal => minus_a.cmp(&minus_b),
_ => cmp_result,
}
}
_ => self.simplify().cmp(&other.simplify()),
}
}
}
Comments