Hello! I have an enum and I want to implement PartialEq for it and for the base type of one of the enums variants. The enum and the impl looks like this:
enum Similarity {
Any(f32),
Certain
}
impl Similarity {
pub fn is_certain(&self) -> bool {
match *self {
Similarity::Certain => true,
Similarity::Any(sim) => (sim - 1.0).abs() < f32::EPSILON
}
}
pub fn in_percent(&self) -> f32 {
match *self {
Similarity::Certain => 1.0,
Similarity::Any(sim) => sim,
}
}
}
Now I want to implement PartialEq for f32 and Similarity, so that I can write both,
println!("{}, {}, {}", Similarity::Certain < Similarity::Any(0.32), Similarity::Certain < 0.32, Similarity::Any(0.32) < 0.22);
and
println!("{}, {}, {}", Similarity::Any(0.32) < Similarity::Certain, 0.32 < Similarity::Certain, 0.22 < Similarity::Any(0.32));
So, normally I would have to implement
impl PartialEq for Similarity
impl PartialOrd for Similarity
impl PartialEq<f32> for Similarity
impl PartialOrd<f32> for Similarity
impl PartialEq<Similarity> for f32
impl PartialOrd<Similarity> for f32
But that is awfully lot of boilerplate code, since the code is nearly identical. So, I'm asking myself: Is there any way to use a generic way? E.g. Use Into / From ?
What I want to archieve is something like this (which does not work):
impl From<f32> for Similarity {
fn from(sim: f32) -> Self {
let sim = Similarity::Any(sim);
if sim.is_certain() {
Similarity::Certain
} else {
sim
}
}
}
impl Into<f32> for Similarity {
fn into(self) -> f32 {
match self {
Similarity::Certain => 1.0,
Similarity::Any(sim) => sim,
}
}
}
impl PartialEq<Into<f32>> for Similarity {
fn eq(&self, other: &Into<f32>) -> bool {
(self.in_percent() - other.into()).abs() < f32::EPSILON
}
fn ne(&self, other: &Into<f32>) -> bool {
(self.in_percent() - other.into()).abs() > f32::EPSILON
}
}
Thanks for any advice!