Struct bulwark_decision::Decision
source · pub struct Decision {
pub accept: f64,
pub restrict: f64,
pub unknown: f64,
}
Expand description
A Decision
represents evidence in favor of either accepting or restricting an operation under consideration.
It is composed of three values: accept
, restrict
and unknown
. Each must be between 0.0 and 1.0 inclusive
and the sum of all three must equal 1.0. The unknown
value represents uncertainty about the evidence, with
a 1.0 unknown
value indicating total uncertainty or a “no opinion” verdict. Similarly, a 1.0 accept
or
restrict
value indicates total certainty that the verdict should be to accept or to restrict, respectively.
This representation allows for a fairly intuitive way of characterizing evidence in favor of or against
blocking an operation, while still capturing any uncertainty. Limiting to two states rather than a wider range of
classification possibilities allows for better performance optimizations, simplifies code readability, and
enables useful transformations like reweighting a Decision
.
This data structure is a two-state Dempster-Shafer
mass function, with the power set represented by the unknown
value. This enables the use of combination rules
to aggregate decisions from multiple sources. However, knowledge of Dempster-Shafer theory should not be necessary.
Fields§
§accept: f64
§restrict: f64
§unknown: f64
Implementations§
source§impl Decision
impl Decision
sourcepub fn accepted(accept: f64) -> Self
pub fn accepted(accept: f64) -> Self
Converts a simple scalar value into a Decision
using the value as the accept
component.
This function is sugar for Decision { accept, 0.0, 0.0 }.scale())
.
§Arguments
accept
- Theaccept
value to set.
§Examples
use approx::assert_relative_eq;
use bulwark_decision::Decision;
assert_relative_eq!(Decision::accepted(1.0), Decision { accept: 1.0, restrict: 0.0, unknown: 0.0 });
assert_relative_eq!(Decision::accepted(0.5), Decision { accept: 0.5, restrict: 0.0, unknown: 0.5 });
assert_relative_eq!(Decision::accepted(0.0), Decision { accept: 0.0, restrict: 0.0, unknown: 1.0 });
sourcepub fn restricted(restrict: f64) -> Self
pub fn restricted(restrict: f64) -> Self
Converts a simple scalar value into a Decision
using the value as the restrict
component.
This function is sugar for Decision { 0.0, restrict, 0.0 }.scale())
.
§Arguments
restrict
- Therestrict
value to set.
§Examples
use approx::assert_relative_eq;
use bulwark_decision::Decision;
assert_relative_eq!(Decision::restricted(1.0), Decision { accept: 0.0, restrict: 1.0, unknown: 0.0 });
assert_relative_eq!(Decision::restricted(0.5), Decision { accept: 0.0, restrict: 0.5, unknown: 0.5 });
assert_relative_eq!(Decision::restricted(0.0), Decision { accept: 0.0, restrict: 0.0, unknown: 1.0 });
sourcepub fn pignistic(&self) -> Self
pub fn pignistic(&self) -> Self
Reassigns unknown mass evenly to accept and restrict.
This function is used to convert to a form that is useful in producing a final outcome.
sourcepub fn is_accepted(&self, threshold: f64) -> bool
pub fn is_accepted(&self, threshold: f64) -> bool
sourcepub fn is_unknown(&self) -> bool
pub fn is_unknown(&self) -> bool
sourcepub fn outcome(
&self,
trust: f64,
suspicious: f64,
restrict: f64,
) -> Result<Outcome, ThresholdError>
pub fn outcome( &self, trust: f64, suspicious: f64, restrict: f64, ) -> Result<Outcome, ThresholdError>
Checks the restrict
value after pignistic
transformation against several threshold values.
The Outcome
s are arranged in ascending order: Trusted
< Accepted
< Suspected
< Restricted
Does not take an accept
threshold to simplify validation. Returns ThresholdError
if threshold values are
either out-of-order or out-of-range. Thresholds must be between 0.0 and 1.0.
§Arguments
trust
- Thetrust
threshold is an upper-bound threshold. If therestrict
value is below it, the operation isTrusted
.suspicious
- Thesuspicious
threshold is a lower-bound threshold that also defines the accepted range. If therestrict
value is above thetrust
threshold and below thesuspicious
threshold, the operation isAccepted
. If therestrict
value is above thesuspicious
threshold but below therestrict
threshold, the operation isSuspected
.restrict
- Therestricted
threshold is a lower-bound threshold. If therestrict
value is above it, the operation isRestricted
.
sourcepub fn clamp(&self) -> Self
pub fn clamp(&self) -> Self
Clamps all values to the 0.0 to 1.0 range.
Does not guarantee that values will sum to 1.0.
sourcepub fn clamp_min_unknown(&self, min: f64) -> Self
pub fn clamp_min_unknown(&self, min: f64) -> Self
sourcepub fn fill_unknown(&self) -> Self
pub fn fill_unknown(&self) -> Self
If the component values sum to less than 1.0, assigns the remainder to the
unknown
value.
sourcepub fn scale_min_unknown(&self, min: f64) -> Self
pub fn scale_min_unknown(&self, min: f64) -> Self
sourcepub fn weight(&self, factor: f64) -> Self
pub fn weight(&self, factor: f64) -> Self
Multiplies the accept
and restrict
by the factor
parameter, replacing the unknown
value with the remainder.
Weights below 1.0 will reduce the weight of a Decision
, while weights above 1.0 will increase it.
A 1.0 weight has no effect on the result, aside from scaling it to a valid range if necessary.
§Arguments
sourcepub fn combine_conjunctive<'a, I>(decisions: I) -> Selfwhere
Self: 'a,
I: IntoIterator<Item = &'a Self>,
pub fn combine_conjunctive<'a, I>(decisions: I) -> Selfwhere
Self: 'a,
I: IntoIterator<Item = &'a Self>,
Calculates the conjunctive combination of a set of decisions, returning a new Decision
as the result.
Unlike combine_murphy
, combine_conjunctive
will produce a NaN
result under
high conflict.
§Arguments
decisions
- TheDecision
s to be combined.
sourcepub fn combine_murphy<'a, I>(decisions: I) -> Selfwhere
Self: 'a,
I: IntoIterator<Item = &'a Self>,
pub fn combine_murphy<'a, I>(decisions: I) -> Selfwhere
Self: 'a,
I: IntoIterator<Item = &'a Self>,
Calculates the Murphy average of a set of decisions, returning a new Decision
as the result.
The Murphy average rule1 takes the mean value of each focal element across all mass functions to create a new mass function. This new mass function is then combined conjunctively with itself N times where N is the total number of functions that were averaged together.
§Arguments
decisions
- TheDecision
s to be combined.
Catherine K. Murphy. 2000. Combining belief functions when evidence conflicts. Decision Support Systems 29, 1 (2000), 1-9. DOI:https://doi.org/10.1016/s0167-9236(99)00084-6 ↩
Trait Implementations§
source§impl AbsDiffEq for Decision
impl AbsDiffEq for Decision
source§fn default_epsilon() -> Self::Epsilon
fn default_epsilon() -> Self::Epsilon
source§fn abs_diff_eq(&self, other: &Self, epsilon: Self::Epsilon) -> bool
fn abs_diff_eq(&self, other: &Self, epsilon: Self::Epsilon) -> bool
source§fn abs_diff_ne(&self, other: &Rhs, epsilon: Self::Epsilon) -> bool
fn abs_diff_ne(&self, other: &Rhs, epsilon: Self::Epsilon) -> bool
AbsDiffEq::abs_diff_eq
.source§impl PartialEq for Decision
impl PartialEq for Decision
source§impl RelativeEq for Decision
impl RelativeEq for Decision
source§fn default_max_relative() -> Self::Epsilon
fn default_max_relative() -> Self::Epsilon
source§fn relative_eq(
&self,
other: &Self,
epsilon: Self::Epsilon,
max_relative: Self::Epsilon,
) -> bool
fn relative_eq( &self, other: &Self, epsilon: Self::Epsilon, max_relative: Self::Epsilon, ) -> bool
source§fn relative_ne(
&self,
other: &Rhs,
epsilon: Self::Epsilon,
max_relative: Self::Epsilon,
) -> bool
fn relative_ne( &self, other: &Rhs, epsilon: Self::Epsilon, max_relative: Self::Epsilon, ) -> bool
RelativeEq::relative_eq
.source§impl UlpsEq for Decision
impl UlpsEq for Decision
source§impl<'v_a> ValidateArgs<'v_a> for Decision
impl<'v_a> ValidateArgs<'v_a> for Decision
type Args = ()
fn validate_args(&self, args: Self::Args) -> Result<(), ValidationErrors>
impl Copy for Decision
impl StructuralPartialEq for Decision
Auto Trait Implementations§
impl Freeze for Decision
impl RefUnwindSafe for Decision
impl Send for Decision
impl Sync for Decision
impl Unpin for Decision
impl UnwindSafe for Decision
Blanket Implementations§
source§impl<T> BorrowMut<T> for Twhere
T: ?Sized,
impl<T> BorrowMut<T> for Twhere
T: ?Sized,
source§fn borrow_mut(&mut self) -> &mut T
fn borrow_mut(&mut self) -> &mut T
source§impl<T> CloneToUninit for Twhere
T: Copy,
impl<T> CloneToUninit for Twhere
T: Copy,
source§unsafe fn clone_to_uninit(&self, dst: *mut T)
unsafe fn clone_to_uninit(&self, dst: *mut T)
clone_to_uninit
)source§impl<T> CloneToUninit for Twhere
T: Clone,
impl<T> CloneToUninit for Twhere
T: Clone,
source§default unsafe fn clone_to_uninit(&self, dst: *mut T)
default unsafe fn clone_to_uninit(&self, dst: *mut T)
clone_to_uninit
)