1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
use std::cmp::Ordering;

#[derive(Copy, Clone, Debug, Eq)]
pub struct Range {
    pub begin: usize,
    pub end: usize,
}

impl Range {
    pub fn new(begin: usize, end: usize) -> Self {
        assert!(begin <= end);
        Range { begin, end }
    }

    pub fn offset(&mut self, offset: usize) {
        self.begin += offset;
        self.end += offset;
    }
}

impl PartialEq for Range {
    fn eq(&self, other: &Self) -> bool {
        if self.begin <= other.begin {
            other.begin < self.end
        } else {
            self.begin < other.end
        }
    }
}

impl Ord for Range {
    fn cmp(&self, other: &Self) -> Ordering {
        if self.eq(other) {
            Ordering::Equal
        } else {
            self.begin.cmp(&other.begin)
        }
    }
}

impl PartialOrd for Range {
    fn partial_cmp(&self, other: &Self) -> Option<Ordering> {
        Some(self.cmp(other))
    }
}

#[cfg(test)]
mod tests {
    use super::*;
    use std::collections::BTreeMap;

    #[test]
    fn test_btreemap() {
        let mut map = BTreeMap::new();
        map.insert(Range::new(0, 10), String::from("0-10"));
        map.insert(Range::new(10, 15), String::from("10-15"));
        assert_eq!(map.get(&Range::new(0, 1)), Some(&String::from("0-10")));
        assert_eq!(map.get(&Range::new(3, 4)), Some(&String::from("0-10")));
        assert_eq!(map.get(&Range::new(10, 11)), Some(&String::from("10-15")));
        assert_eq!(map.get(&Range::new(15, 16)), None);
    }
}