1use lambda_calculus::term::*;
4use self::Error::*;
5
6#[derive(Debug, PartialEq)]
8pub enum Error {
9 NotATerm
11}
12
13pub fn from_bits(input: &[u8]) -> Result<Term, Error> {
25 if let Some((result, _)) = _from_bits(input) {
26 Ok(result)
27 } else {
28 Err(NotATerm)
29 }
30}
31
32fn _from_bits(input: &[u8]) -> Option<(Term, &[u8])> {
33 if input.is_empty() { return None }
34
35 if [9, 10, 13, 32].contains(&input[0]) {
36 _from_bits(&input[1..]) } else {
38 match &input[0..2] {
39 b"00" => {
40 if let Some((term, rest)) = _from_bits(&input[2..]) {
41 Some((abs(term), rest))
42 } else {
43 None
44 }
45 },
46 b"01" => {
47 if let Some((term1, rest1)) = _from_bits(&input[2..]) {
48 if let Some((term2, rest2)) = _from_bits(rest1) {
49 Some((app(term1, term2), rest2))
50 } else {
51 None
52 }
53 } else {
54 None
55 }
56 },
57 b"10" | b"11" => {
58 let i = input.iter().take_while(|&b| *b == b'1').count();
59 if input[2..].is_empty() {
60 Some((Var(i), &*b""))
61 } else {
62 Some((Var(i), &input[i+1..]))
63 }
64 },
65 _ => None
66 }
67 }
68}
69
70pub fn to_bits(term: &Term) -> Vec<u8> {
82 let mut output = Vec::new();
83 _to_bits(term, &mut output);
84
85 output
86}
87
88fn _to_bits(term: &Term, output: &mut Vec<u8>) {
89 match *term {
90 Var(i) => {
91 for _ in 0..i { output.push(b'1') }
92 output.push(b'0');
93 }
94 Abs(ref t) => {
95 output.extend_from_slice(b"00");
96 output.append(&mut to_bits(t));
97 }
98 App(ref t1, ref t2) => {
99 output.extend_from_slice(b"01");
100 output.append(&mut to_bits(t1));
101 output.append(&mut to_bits(t2));
102 }
103 }
104}
105
106pub fn compress(bits: &[u8]) -> Vec<u8> {
117 let length = bits.len();
118 let mut output = Vec::with_capacity(length / 8 + 1);
119 let mut pos = 0;
120
121 while pos <= length - 8 {
122 output.push(bits_to_byte(&bits[pos..(pos + 8)]));
123 pos += 8;
124 }
125
126 if pos != length {
127 let mut last_byte = Vec::with_capacity(8);
128 last_byte.extend_from_slice(&bits[pos..]);
129 for _ in 0..(8 - (length - pos)) { last_byte.push(b'0') }
130 output.push(bits_to_byte(&last_byte));
131 }
132
133 output
134}
135
136fn bits_to_byte(bits: &[u8]) -> u8 {
137 bits.iter().fold(0, |acc, &b| acc * 2 + (b - 48))
138}
139
140pub fn decompress(bytes: &[u8]) -> Vec<u8> {
151 let mut output = Vec::with_capacity(bytes.len() * 8);
152
153 for byte in bytes {
154 output.extend_from_slice(format!("{:08b}", byte).as_bytes());
155 }
156
157 output
158}
159
160#[cfg(test)]
161mod test {
162 use super::*;
163
164 const QUINE: &'static [u8; 66] =
165 b"000101100100011010000000000001011011110010111100111111011111011010";
166
167 const PRIMES: &'static [u8; 167] =
168 b"00010001100110010100011010000000010110000010010001010111110111101001000110100001\
169 11001101000000000010110111001110011111110111100000000111110011011100000010110000\
170 0110110";
171
172 const BLC: &'static [u8; 232] =
173 b"01010001101000000001010110000000000111100001011111100111100001011100111100000011\
174 11000010110110111001111100001111100001011110100111010010110011100001101100001011\
175 111000011111000011100110111101111100111101110110000110010001101000011010";
176
177 #[test]
178 fn variables() {
179 assert_eq!(from_bits(b"10"), Ok(Var(1)));
180 assert_eq!(from_bits(b"110"), Ok(Var(2)));
181 assert_eq!(from_bits(b"1110"), Ok(Var(3)));
182 }
183
184 #[test]
185 fn abstractions() {
186 assert_eq!(from_bits(b"0010"), Ok(abs(Var(1))));
187 assert_eq!(from_bits(b"000010"), Ok(abs!(2, Var(1))));
188 assert_eq!(from_bits(b"00000010"), Ok(abs!(3, Var(1))));
189 }
190
191 #[test]
192 fn applications() {
193 assert_eq!(from_bits(b"011010"), Ok(app(Var(1), Var(1))));
194 assert_eq!(from_bits(b"0110110"), Ok(app(Var(1), Var(2))));
195 assert_eq!(from_bits(b"0111010"), Ok(app(Var(2), Var(1))));
196 }
197
198 #[test]
199 fn ignoring_whitespaces() {
200 assert_eq!(from_bits(b"00 00\t00\n10\r\n"), Ok(abs!(3, Var(1))));
201 }
202
203 #[test]
204 fn from_bits_and_back() {
205 let k = b"0000110";
206 let v15 = b"1111111111111110";
207 let s = b"00000001011110100111010";
208 let succ = b"000000011100101111011010";
209
210 assert_eq!(to_bits(&from_bits(&*k).unwrap()), k);
211 assert_eq!(to_bits(&from_bits(&*v15).unwrap()), v15);
212 assert_eq!(to_bits(&from_bits(&*s).unwrap()), s);
213 assert_eq!(to_bits(&from_bits(&*succ).unwrap()), succ);
214 assert_eq!(to_bits(&from_bits(&*QUINE).unwrap()), &QUINE[..]);
215 assert_eq!(to_bits(&from_bits(&*PRIMES).unwrap()), Vec::from(&PRIMES[..]));
216 assert_eq!(to_bits(&from_bits(&*BLC).unwrap()), Vec::from(&BLC[..]));
217 }
218
219 #[test]
220 fn compression() {
221 let primes_c = compress(&PRIMES[..]);
222 assert_eq!(primes_c.first().unwrap(), &0x11);
223 assert_eq!(primes_c.last().unwrap(), &0x6c);
224
225 let blc_c = compress(&BLC[..]);
226 assert_eq!(blc_c.first().unwrap(), &0x51);
227 assert_eq!(blc_c.last().unwrap(), &0x1a);
228 }
229
230 #[test]
231 fn decompression() {
232 let s_c = vec![0x1, 0x7a, 0x74];
233 assert_eq!(compress(&decompress(&s_c)), s_c);
234 }
235
236 #[test]
237 fn compress_decompress() {
238 assert_eq!(decompress(&compress(&BLC[..])), Vec::from(&BLC[..]));
239 }
240}