1#![doc = include_str!("../README.md")]
4
5#[derive(Clone, Copy, Debug, PartialEq)]
11pub struct HDBool(u8);
12
13impl HDBool {
14 pub fn new(val: bool) -> Self {
16 HDBool(if val { u8::MAX } else { u8::MIN })
17 }
18
19 pub fn from_u8(raw: u8) -> Self {
21 HDBool(Self::refresh(raw))
22 }
23
24 pub fn as_u8(&self) -> u8 {
26 self.0
27 }
28
29 pub fn to_bool(&self) -> bool {
31 match self.0 {
33 0xFF => true,
34 0x00 => false,
35 _ => HDBool::refresh(self.0) == u8::MAX,
36 }
37 }
38
39 fn refresh(raw: u8) -> u8 {
41 if raw.count_ones() > 4 {
42 u8::MAX
43 } else {
44 u8::MIN
45 }
46 }
47}
48
49
50#[cfg(test)]
51mod tests {
52 use std::u8;
53
54 use super::*;
55
56 #[test]
57 fn test_normal_bool_representation() {
58 assert_eq!(true as u8, 0b_0000_0001_u8);
59 assert_eq!(false as u8, 0b_0000_0000_u8);
60 assert_ne!(true as u8, 0b_1111_1111_u8);
61 assert_ne!(false as u8, 0b_1000_0000_u8);
62 assert_ne!(true as u8, 0b_0100_0010_u8);
63 assert_ne!(false as u8, 0b_0010_0001_u8);
64
65 assert_ne!(true as u8, HDBool::new(true).as_u8());
66 assert_ne!(false as u8, HDBool::new(true).as_u8());
67 assert_ne!(true as u8, HDBool::new(false).as_u8());
68 assert_eq!(false as u8, HDBool::new(false).as_u8());
69
70 assert!(true);
71 assert!(!false);
72 }
73
74 #[test]
75 fn test_hdbool() {
76 assert_eq!(HDBool::new(true), HDBool(u8::MAX));
77 assert_eq!(HDBool::new(false), HDBool(u8::MIN));
78 assert_eq!(HDBool::new(true).to_bool(), true);
79 assert_eq!(HDBool::new(false).to_bool(), false);
80 assert_eq!(HDBool::new(true).as_u8(), u8::MAX);
81 assert_eq!(HDBool::new(false).as_u8(), u8::MIN);
82
83 assert_eq!(HDBool::from_u8(0b_1111_1111_u8), HDBool(u8::MAX));
84 assert_eq!(HDBool::from_u8(0b_0000_0000_u8), HDBool(u8::MIN));
85 assert_eq!(HDBool::from_u8(0b_1111_1111_u8).to_bool(), true);
86 assert_eq!(HDBool::from_u8(0b_0000_0000_u8).to_bool(), false);
87 assert_eq!(HDBool::from_u8(0b_1111_1111_u8).as_u8(), u8::MAX);
88 assert_eq!(HDBool::from_u8(0b_0000_0000_u8).as_u8(), u8::MIN);
89 assert_eq!(HDBool::from_u8(0b_1111_1110_u8).to_bool(), true);
90 assert_eq!(HDBool::from_u8(0b_0000_0001_u8).to_bool(), false);
91
92 assert_eq!(HDBool(u8::MAX).as_u8(), 0b_1111_1111_u8);
93 assert_eq!(HDBool(u8::MIN).as_u8(), 0b_0000_0000_u8);
94 assert_ne!(HDBool(u8::MAX).as_u8(), 0b_0000_0000_u8);
95 assert_ne!(HDBool(u8::MIN).as_u8(), 0b_1111_1111_u8);
96 assert_ne!(HDBool(u8::MAX).as_u8(), HDBool::new(false).as_u8());
97 assert_ne!(HDBool(u8::MIN).as_u8(), HDBool::new(true).as_u8());
98
99 assert!(HDBool(u8::MAX).to_bool());
100 assert!(!HDBool(u8::MIN).to_bool());
101
102 assert_eq!(HDBool(u8::MAX).to_bool(), true);
103 assert_eq!(HDBool(u8::MIN).to_bool(), false);
104 assert_ne!(HDBool(u8::MAX).to_bool(), false);
105 assert_ne!(HDBool(u8::MIN).to_bool(), true);
106 assert_eq!(HDBool(u8::MAX).as_u8(), u8::MAX);
107 assert_eq!(HDBool(u8::MIN).as_u8(), u8::MIN);
108
109 assert_ne!(HDBool(HDBool::refresh(0b_1111_1111_u8)).to_bool(), false);
110 assert_ne!(HDBool(HDBool::refresh(0b_0000_0000_u8)).to_bool(), true);
111 assert_eq!(HDBool(HDBool::refresh(0b_1111_1111_u8)).to_bool(), true);
112 assert_eq!(HDBool(HDBool::refresh(0b_0000_0000_u8)).to_bool(), false);
113 assert_eq!(HDBool(HDBool::refresh(0b_1111_1111_u8)).as_u8(), u8::MAX);
114 assert_eq!(HDBool(HDBool::refresh(0b_0000_0000_u8)).as_u8(), u8::MIN);
115 assert_eq!(HDBool(HDBool::refresh(0b_0000_1111_u8)).as_u8(), u8::MIN);
116 assert_eq!(HDBool(HDBool::refresh(0b_1111_0000_u8)).as_u8(), u8::MIN);
117 assert_eq!(HDBool(HDBool::refresh(0b_0000_1111_u8)).to_bool(), false);
118 assert_eq!(HDBool(HDBool::refresh(0b_1111_0000_u8)).to_bool(), false);
119 assert_eq!(HDBool(HDBool::refresh(0b_0100_1111_u8)).to_bool(), true);
120
121 assert_eq!(HDBool::refresh(0b_1111_1111_u8), u8::MAX);
122 assert_eq!(HDBool::refresh(0b_0000_0000_u8), u8::MIN);
123 assert_eq!(HDBool::refresh(0b_1111_1110_u8), u8::MAX);
124 assert_eq!(HDBool::refresh(0b_0000_0001_u8), u8::MIN);
125 assert_eq!(HDBool::refresh(0b_1111_1100_u8), u8::MAX);
126 assert_eq!(HDBool::refresh(0b_0000_0011_u8), u8::MIN);
127 assert_eq!(HDBool::refresh(0b_1111_1000_u8), u8::MAX);
128 assert_eq!(HDBool::refresh(0b_0000_0111_u8), u8::MIN);
129 assert_eq!(HDBool::refresh(0b_1111_0000_u8), u8::MIN);
130 assert_eq!(HDBool::refresh(0b_0000_1111_u8), u8::MIN);
131 }
132
133 #[test]
134 fn test_memory_footprint() {
135 assert_eq!(std::mem::size_of::<HDBool>(), 1);
136 assert_eq!(std::mem::size_of::<u8>(), 1);
137 assert_eq!(std::mem::size_of::<bool>(), 1);
138 assert!(std::mem::size_of::<HDBool>() <= std::mem::size_of::<u8>());
139
140 assert_eq!(std::mem::size_of_val(&HDBool::new(true)), 1);
141 assert_eq!(std::mem::size_of_val(&HDBool::new(false)), 1);
142 assert_eq!(std::mem::size_of_val(&HDBool::from_u8(0b_1111_1111_u8)), 1);
143 assert_eq!(std::mem::size_of_val(&HDBool::from_u8(0b_0000_0000_u8)), 1);
144 assert_eq!(std::mem::size_of_val(&HDBool(u8::MAX)), 1);
145 assert_eq!(std::mem::size_of_val(&HDBool(u8::MIN)), 1);
146 assert!(std::mem::size_of_val(&HDBool::new(true)) <= std::mem::size_of_val(&u8::MAX));
147 }
148
149 #[test]
150 fn test_equality_of_different_representations_for_hdbools() {
151 assert_eq!(HDBool::new(true).as_u8(), 0b_1111_1111_u8);
152 assert_eq!(HDBool::new(true).as_u8(), u8::MAX);
153 assert_eq!(HDBool::new(false).as_u8(), 0b_0000_0000_u8);
154 assert_eq!(HDBool::new(false).as_u8(), u8::MIN);
155 }
156
157}