weighted_list/
weighted_item.rs

1use std::{
2    fmt
3};
4
5use crate::root::*;
6
7
8/// An item in a `WeightedList`, with a `value` of type `V` and a `weight` of numerical type `W`.
9/// 
10/// For consistency and layout, `weight` always comes before `value` when ordering is relevant.
11/// 
12/// You should rarely find yourself constructing a `WeightedItem` by hand – instead, you'll usually interact with existing instances from a `WeightedList`.
13#[derive(Debug, Clone, Eq, PartialEq, Hash)]
14pub struct WeightedItem<V, W: Weight>
15{
16    /// The weight of the item. A non-negative number. `0` is technically valid, but not advised.
17    pub weight: W,
18
19    /// The value stored in the item.
20    pub value: V,
21}
22
23// == CONSTRUCTORS == //
24impl<V, W: Weight> WeightedItem<V,W>
25{
26    /// Construct a `WeightedItem` with `value` and a weight of `1`.
27    pub fn unit(value: V) -> Self
28    {
29        Self {
30            weight: W::one(),
31            value
32        }
33    }
34
35    /// Construct a `WeightedItem` with `value` and `weight`.
36    pub fn new(weight: W, value: V) -> Self
37    {
38        Self { weight, value }
39    }
40
41    /// Construct a `WeightedItem` from a `(weight, value)` pair.
42    pub fn from((weight, value): (W, V)) -> Self
43    {
44        Self { weight, value }
45    }
46}
47
48/// Construct a `WeightedItem` from a `(weight, value)` pair.
49/// 
50/// # Usage
51/// 
52/// ```
53/// # use weighted_list::*;
54/// let item = wit!(2.0, "sup");
55/// assert_eq!(item, WeightedItem::new(2.0, "sup"));
56/// ```
57#[macro_export]
58macro_rules! wit {
59    ( $weight: expr, $value: expr ) => {
60        WeightedItem::new($weight, $value)
61    };
62}
63
64// == CONVERSIONS == //
65impl<V, W: Weight> From<WeightedItem<V,W>> for (W, V)
66{
67    fn from(item: WeightedItem<V,W>) -> Self {
68        (item.weight, item.value)
69    }
70}
71
72// == TRAITS == //
73impl<V: fmt::Display, W: Weight> fmt::Display for WeightedItem<V,W>
74{
75    fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result
76    {
77        write!(f, "{{ {}, {} }}", self.weight, self.value)
78    }
79}
80
81impl<V: Eq, W: Weight + Ord> Ord for WeightedItem<V,W>
82{
83    fn cmp(&self, other: &Self) -> std::cmp::Ordering
84    {
85        self.weight.cmp(&other.weight)
86        // .then(self.value.cmp(&other.value))
87    }
88}
89
90impl<V: Eq, W: Weight> PartialOrd for WeightedItem<V,W>
91{
92    fn partial_cmp(&self, other: &Self) -> Option<std::cmp::Ordering>
93    {
94        self.weight.partial_cmp(&other.weight)
95    }
96}