1pub trait Bool {
19 const VALUE: bool;
21
22 type Not: Bool;
26
27 type Implies<B: Bool>: Bool;
31}
32
33pub struct True {}
35
36impl Bool for True {
37 const VALUE: bool = true;
38
39 type Not = False;
40
41 type Implies<B: Bool> = B;
42}
43
44pub struct False {}
46
47impl Bool for False {
48 const VALUE: bool = false;
49
50 type Not = True;
51
52 type Implies<B: Bool> = True;
53}
54
55#[allow(type_alias_bounds)]
58pub type Not<B>
59where
60 B: Bool,
61= <B as Bool>::Not;
62
63#[allow(type_alias_bounds)]
66pub type Implies<A, B>
67where
68 A: Bool,
69 B: Bool,
70= <A as Bool>::Implies<B>;
71
72#[allow(type_alias_bounds)]
75pub type And<A, B>
76where
77 A: Bool,
78 B: Bool,
79= Not<Implies<A, Not<B>>>;
80
81#[allow(type_alias_bounds)]
84pub type Or<A, B>
85where
86 A: Bool,
87 B: Bool,
88= Not<And<Not<A>, Not<B>>>; #[allow(type_alias_bounds)]
93pub type Xor<A, B>
94where
95 A: Bool,
96 B: Bool,
97= And<Or<A, B>, Not<And<A, B>>>;
98
99#[allow(type_alias_bounds)]
102pub type Iff<A, B>
103where
104 A: Bool,
105 B: Bool,
106= And<Implies<A, B>, Implies<B, A>>;
107
108#[cfg(test)]
109mod tests {
110 use crate::type_utils::assert_type_eq;
111
112 use super::*;
113
114 #[test]
115 #[allow(clippy::bool_assert_comparison)]
116 fn value() {
117 assert_eq!(True::VALUE, true);
118 assert_eq!(False::VALUE, false);
119 }
120
121 #[test]
122 fn not() {
123 assert_type_eq::<False, Not<True>>();
124 assert_type_eq::<True, Not<False>>();
125 }
126
127 #[test]
128 fn and() {
129 assert_type_eq::<True, And<True, True>>();
130 assert_type_eq::<False, And<False, True>>();
131 assert_type_eq::<False, And<True, False>>();
132 assert_type_eq::<False, And<False, False>>();
133 }
134
135 #[test]
136 fn or() {
137 assert_type_eq::<True, Or<True, True>>();
138 assert_type_eq::<True, Or<False, True>>();
139 assert_type_eq::<True, Or<True, False>>();
140 assert_type_eq::<False, Or<False, False>>();
141 }
142
143 #[test]
144 fn xor() {
145 assert_type_eq::<False, Xor<True, True>>();
146 assert_type_eq::<True, Xor<False, True>>();
147 assert_type_eq::<True, Xor<True, False>>();
148 assert_type_eq::<False, Xor<False, False>>();
149 }
150
151 #[test]
152 fn implies() {
153 assert_type_eq::<True, Implies<True, True>>();
154 assert_type_eq::<True, Implies<False, True>>();
155 assert_type_eq::<False, Implies<True, False>>();
156 assert_type_eq::<True, Implies<False, False>>();
157 }
158}