nil_core/behavior/
score.rs1use derive_more::Into;
5use std::cmp::Ordering;
6use std::fmt::Debug;
7use std::ops::{Add, AddAssign, Div, DivAssign, Mul, MulAssign, Sub, SubAssign};
8
9#[derive(Copy, Debug, Into)]
10#[derive_const(Clone)]
11pub struct BehaviorScore(f64);
12
13impl BehaviorScore {
14 pub const MIN: Self = BehaviorScore(0.0);
15 pub const MAX: Self = BehaviorScore(1.0);
16
17 #[inline]
18 pub const fn new(score: f64) -> Self {
19 debug_assert!(score.is_finite());
20 debug_assert!(!score.is_subnormal());
21 Self(score.clamp(Self::MIN.0, Self::MAX.0))
22 }
23
24 #[inline]
25 pub const fn is_within_range(self, other: BehaviorScore, range: f64) -> bool {
26 (self.0 - other.0).abs() < range
27 }
28}
29
30impl const Default for BehaviorScore {
31 fn default() -> Self {
32 Self::MIN
33 }
34}
35
36impl const From<f64> for BehaviorScore {
37 fn from(score: f64) -> Self {
38 Self::new(score)
39 }
40}
41
42impl const PartialEq for BehaviorScore {
43 fn eq(&self, other: &Self) -> bool {
44 matches!(self.0.total_cmp(&other.0), Ordering::Equal)
45 }
46}
47
48impl const Eq for BehaviorScore {}
49
50impl const PartialOrd for BehaviorScore {
51 fn partial_cmp(&self, other: &Self) -> Option<Ordering> {
52 Some(self.cmp(other))
53 }
54}
55
56impl const Ord for BehaviorScore {
57 fn cmp(&self, other: &Self) -> Ordering {
58 self.0.total_cmp(&other.0)
59 }
60}
61
62impl const PartialEq<f64> for BehaviorScore {
63 fn eq(&self, other: &f64) -> bool {
64 self.0.eq(other)
65 }
66}
67
68impl const PartialOrd<f64> for BehaviorScore {
69 fn partial_cmp(&self, other: &f64) -> Option<Ordering> {
70 self.0.partial_cmp(other)
71 }
72}
73
74impl const Add<f64> for BehaviorScore {
75 type Output = BehaviorScore;
76
77 fn add(self, rhs: f64) -> Self::Output {
78 BehaviorScore::new(self.0 + rhs)
79 }
80}
81
82impl const AddAssign<f64> for BehaviorScore {
83 fn add_assign(&mut self, rhs: f64) {
84 *self = *self + rhs;
85 }
86}
87
88impl const Sub<f64> for BehaviorScore {
89 type Output = BehaviorScore;
90
91 fn sub(self, rhs: f64) -> Self::Output {
92 BehaviorScore::new(self.0 - rhs)
93 }
94}
95
96impl const SubAssign<f64> for BehaviorScore {
97 fn sub_assign(&mut self, rhs: f64) {
98 *self = *self - rhs;
99 }
100}
101
102impl const Mul<f64> for BehaviorScore {
103 type Output = BehaviorScore;
104
105 fn mul(self, rhs: f64) -> Self::Output {
106 BehaviorScore::new(self.0 * rhs)
107 }
108}
109
110impl const MulAssign<f64> for BehaviorScore {
111 fn mul_assign(&mut self, rhs: f64) {
112 *self = *self * rhs;
113 }
114}
115
116impl const Div<f64> for BehaviorScore {
117 type Output = BehaviorScore;
118
119 fn div(self, rhs: f64) -> Self::Output {
120 BehaviorScore::new(self.0 / rhs)
121 }
122}
123
124impl const DivAssign<f64> for BehaviorScore {
125 fn div_assign(&mut self, rhs: f64) {
126 *self = *self / rhs;
127 }
128}