diff options
author | Federico Igne <git@federicoigne.com> | 2022-06-23 19:06:22 +0100 |
---|---|---|
committer | Federico Igne <git@federicoigne.com> | 2022-06-23 19:06:22 +0100 |
commit | 120d53c0ff20574866ce10fa0538fb8b0dd2ef82 (patch) | |
tree | 4ac370f9b525c713635a6af09530f20758e91fb7 /day3/src | |
parent | 5d99706992101d684c9920475e2ecaab65ba21ba (diff) | |
download | aoc-120d53c0ff20574866ce10fa0538fb8b0dd2ef82.tar.gz aoc-120d53c0ff20574866ce10fa0538fb8b0dd2ef82.zip |
Reorganize repository structure
Diffstat (limited to 'day3/src')
-rw-r--r-- | day3/src/main.rs | 65 |
1 files changed, 0 insertions, 65 deletions
diff --git a/day3/src/main.rs b/day3/src/main.rs deleted file mode 100644 index d943de0..0000000 --- a/day3/src/main.rs +++ /dev/null | |||
@@ -1,65 +0,0 @@ | |||
1 | use std::fs; | ||
2 | use std::path::Path; | ||
3 | |||
4 | const ENTRY_LENGTH: usize = 12; | ||
5 | |||
6 | /* AOC21 Day 3: https://adventofcode.com/2021/day/3 */ | ||
7 | fn main() { | ||
8 | let input = Path::new("resources").join("input.txt"); | ||
9 | let content = fs::read_to_string(input).expect("Unable to read input file"); | ||
10 | let report: Vec<u32> = content.lines().map(|l| u32::from_str_radix(l,2).expect("Malformed input")).collect(); | ||
11 | ex1(&report); | ||
12 | ex2(report); | ||
13 | } | ||
14 | |||
15 | fn ex1(report: &[u32]) { | ||
16 | let gamma = compute_gamma(&report); | ||
17 | let epsilon = compute_epsilon(gamma); | ||
18 | println!("Ex1: the result is {} ({} * {})", gamma*epsilon, gamma, epsilon); | ||
19 | } | ||
20 | |||
21 | fn compute_gamma(report: &[u32]) -> u32 { | ||
22 | let length = report.len() as u32; | ||
23 | let mut counter: Vec<u32> = vec![0; ENTRY_LENGTH]; | ||
24 | report.iter().for_each(|entry| counter.iter_mut().enumerate().for_each(|(i,v)| *v += (entry >> i) & 1)); | ||
25 | counter.iter().enumerate().map(|(i,v)| if v*2 > length { 1 << i } else { 0 }).sum() | ||
26 | } | ||
27 | |||
28 | fn compute_epsilon(gamma: u32) -> u32 { | ||
29 | gamma ^ ((1 << ENTRY_LENGTH)-1) | ||
30 | } | ||
31 | |||
32 | fn ex2(report: Vec<u32>) { | ||
33 | let o2 = compute_rating(report.clone(), ENTRY_LENGTH, 1); | ||
34 | let co2 = compute_rating(report, ENTRY_LENGTH, 0); | ||
35 | println!("Ex2: the result is {} ({} * {})", o2*co2, o2, co2); | ||
36 | } | ||
37 | |||
38 | fn compute_rating(mut ratings: Vec<u32>, bit: usize, criterion: u32) -> u32 { | ||
39 | if ratings.len() == 1 || bit == 0 { | ||
40 | ratings[0] | ||
41 | } else { | ||
42 | let ones = ratings.iter().filter(|&r| ((r >> bit-1) & 1) == 1).count(); | ||
43 | let sel = if 2*ones < ratings.len() { 1^criterion } else { criterion }; | ||
44 | ratings.retain(|&r| ((r >> bit-1) & 1) == sel); | ||
45 | compute_rating(ratings, bit-1, criterion) | ||
46 | } | ||
47 | } | ||
48 | |||
49 | #[cfg(test)] | ||
50 | mod tests { | ||
51 | use super::*; | ||
52 | |||
53 | const TEST_INPUT: [u32;12] = [0b00100, 0b11110, 0b10110, 0b10111, 0b10101, 0b01111, 0b00111, 0b11100, 0b10000, 0b11001, 0b00010, 0b01010]; | ||
54 | const ENTRY_LENGTH: usize = 5; | ||
55 | |||
56 | #[test] | ||
57 | fn oxygen_generator_rating() { | ||
58 | assert_eq!(23,compute_rating(Vec::from(TEST_INPUT), ENTRY_LENGTH, 1)) | ||
59 | } | ||
60 | |||
61 | #[test] | ||
62 | fn co2_scrubber_rating() { | ||
63 | assert_eq!(10,compute_rating(Vec::from(TEST_INPUT), ENTRY_LENGTH, 0)) | ||
64 | } | ||
65 | } | ||