feat: day 2

This commit is contained in:
Lucy 2024-12-02 10:02:52 +01:00
parent 7f5c391656
commit 0349ca6a7f
4 changed files with 84 additions and 12 deletions

6
inputs/day02/example.txt Normal file
View file

@ -0,0 +1,6 @@
7 6 4 2 1
1 2 7 8 9
9 7 6 2 1
1 3 2 4 5
8 6 4 4 1
1 3 6 7 9

View file

@ -1,32 +1,31 @@
pub fn pt1(input: &str) -> i32 {
pub fn pt1(input: &str) -> usize {
let elems = input
.lines()
.filter_map(|l| l.split_once(" "))
.map(|(l, r)| (l.parse::<i32>(), r.parse::<i32>()))
.map(|(l, r)| (l.parse::<usize>(), r.parse::<usize>()))
.filter(|(l, r)| l.is_ok() && r.is_ok())
.map(|(l, r)| (l.unwrap(), r.unwrap()));
let mut lefts = elems.clone().map(|(l, _)| l).collect::<Vec<_>>();
let mut rights = elems.map(|(_, r)| r).collect::<Vec<_>>();
lefts.sort_unstable();
rights.sort_unstable();
let res: u32 = lefts
lefts
.iter()
.zip(rights.iter())
.map(|(l, r)| l.abs_diff(*r))
.sum();
res as i32
.sum()
}
pub fn pt2(input: &str) -> i32 {
pub fn pt2(input: &str) -> usize {
let elems = input
.lines()
.filter_map(|l| l.split_once(" "))
.map(|(l, r)| (l.parse::<i32>(), r.parse::<i32>()))
.map(|(l, r)| (l.parse::<usize>(), r.parse::<usize>()))
.filter(|(l, r)| l.is_ok() && r.is_ok())
.map(|(l, r)| (l.unwrap(), r.unwrap()));
let lefts = elems.clone().map(|(l, _)| l);
let rights = elems.map(|(_, r)| r).collect::<Vec<_>>();
lefts
.map(|l| rights.clone().iter().filter(|r| **r == l).count() as i32 * l)
.map(|l| rights.clone().iter().filter(|r| **r == l).count() * l)
.sum()
}

64
src/day02.rs Normal file
View file

@ -0,0 +1,64 @@
use std::cmp::Ordering;
pub fn pt1(input: &str) -> usize {
input
.lines()
.map(|l| {
l.split_whitespace()
.map(|s| s.parse::<i32>().unwrap())
.collect::<Vec<_>>()
})
.filter(|v| is_safe(v))
.count()
}
pub fn is_safe(it: &[i32]) -> bool {
assert!((it.len() >= 2), "Not enough elements");
let first = it.first().unwrap();
let second = it[1];
match first.cmp(&second) {
Ordering::Less => it.windows(2).map(|w| w[1] - w[0]).all(|e| e > 0 && e <= 3),
Ordering::Equal => false,
Ordering::Greater => it.windows(2).map(|w| w[0] - w[1]).all(|e| e > 0 && e <= 3),
}
}
pub fn is_safe_skipping_one(it: &[i32]) -> bool {
is_safe(it)
|| (0..it.len()).any(|index_to_skip| {
let mut to_test = it.to_owned();
to_test.remove(index_to_skip);
is_safe(&to_test)
})
}
pub fn pt2(input: &str) -> usize {
input
.lines()
.map(|l| {
l.split_whitespace()
.map(|s| s.parse::<i32>().unwrap())
.collect::<Vec<_>>()
})
.filter(|v| is_safe_skipping_one(v))
.count()
}
#[cfg(test)]
mod tests {
use std::fs::read_to_string;
use crate::day02::{pt1, pt2};
#[test]
pub fn test_pt1() {
let input =
read_to_string("./inputs/day02/example.txt").expect("Missing example.txt for day02");
assert_eq!(pt1(&input), 2)
}
#[test]
pub fn test_pt2() {
let input =
read_to_string("./inputs/day02/example.txt").expect("Missing example.txt for day02");
assert_eq!(pt2(&input), 4)
}
}

View file

@ -1,11 +1,14 @@
use std::fs::read_to_string;
use crate::day01::{pt1, pt2};
mod day01;
mod day02;
fn main() {
println!("day 01!");
let input = read_to_string("./inputs/day01/input.txt").expect("Missing input.txt for day01");
println!("And the result is: {}", pt1(&input));
println!("Part 2: {}", pt2(&input));
println!("And the result is: {}", day01::pt1(&input));
println!("Part 2: {}", day01::pt2(&input));
println!("day 02!");
let input = read_to_string("./inputs/day02/input.txt").expect("Missing input.txt for day02");
println!("And the result is: {}", day02::pt1(&input));
println!("Part 2: {}", day02::pt2(&input));
}