A input/day13/example => input/day13/example +15 -0
@@ 0,0 1,15 @@
+Button A: X+94, Y+34
+Button B: X+22, Y+67
+Prize: X=8400, Y=5400
+
+Button A: X+26, Y+66
+Button B: X+67, Y+21
+Prize: X=12748, Y=12176
+
+Button A: X+17, Y+86
+Button B: X+84, Y+37
+Prize: X=7870, Y=6450
+
+Button A: X+69, Y+23
+Button B: X+27, Y+71
+Prize: X=18641, Y=10279
A src/day13/mod.rs => src/day13/mod.rs +11 -0
@@ 0,0 1,11 @@
+use std::path::Path;
+
+mod part1;
+mod part2;
+
+pub fn solve(input: &Path) -> anyhow::Result<()> {
+ println!("part one: {}", part1::part_one(input)?);
+ println!("part two: {}", part2::part_two(input)?);
+
+ Ok(())
+}
A src/day13/part1.rs => src/day13/part1.rs +97 -0
@@ 0,0 1,97 @@
+use std::{
+ fs::File,
+ io::{BufRead, BufReader},
+ path::Path,
+};
+
+#[derive(Debug)]
+struct M {
+ a: P,
+ b: P,
+ p: P,
+}
+
+impl M {
+ fn from_lines(lines: &[String]) -> Self {
+ let a_line = &lines[0];
+ let b_line = &lines[1];
+ let p_line = &lines[2];
+
+ Self {
+ a: P {
+ x: a_line[&a_line.find("X").unwrap() + 2..a_line.find(",").unwrap()]
+ .parse()
+ .unwrap(),
+ y: a_line[&a_line.find("Y").unwrap() + 2..a_line.len()]
+ .parse()
+ .unwrap(),
+ },
+ b: P {
+ x: b_line[&b_line.find("X").unwrap() + 2..b_line.find(",").unwrap()]
+ .parse()
+ .unwrap(),
+ y: b_line[&b_line.find("Y").unwrap() + 2..b_line.len()]
+ .parse()
+ .unwrap(),
+ },
+ p: P {
+ x: p_line[&p_line.find("X").unwrap() + 2..p_line.find(",").unwrap()]
+ .parse()
+ .unwrap(),
+ y: p_line[&p_line.find("Y").unwrap() + 2..p_line.len()]
+ .parse()
+ .unwrap(),
+ },
+ }
+ }
+}
+
+#[derive(Debug)]
+struct P {
+ x: usize,
+ y: usize,
+}
+
+pub fn part_one(input: &Path) -> anyhow::Result<usize> {
+ let reader = BufReader::new(File::open(input)?);
+
+ let machines: Vec<M> = reader
+ .lines()
+ .filter_map(|l| {
+ let l = l.unwrap();
+ if !l.is_empty() {
+ Some(l)
+ } else {
+ None
+ }
+ })
+ .collect::<Vec<String>>()
+ .chunks(3)
+ .map(|l| -> M { M::from_lines(l) })
+ .collect();
+
+ let mut answer = 0;
+ for machine in machines {
+ let mut oks: Vec<usize> = vec![];
+ let (mut x, mut y) = (0, 0);
+ 'a: for a in 1..101 {
+ x += machine.a.x;
+ y += machine.a.y;
+ let (mut x, mut y) = (x, y);
+ for b in 1..101 {
+ x += machine.b.x;
+ y += machine.b.y;
+ if x == machine.p.x && y == machine.p.y {
+ oks.push(a * 3 + b);
+ continue 'a;
+ }
+ }
+ }
+ if !oks.is_empty() {
+ oks.sort();
+ answer += oks.first().unwrap();
+ }
+ }
+
+ Ok(answer)
+}
A src/day13/part2.rs => src/day13/part2.rs +94 -0
@@ 0,0 1,94 @@
+use std::{
+ fs::File,
+ io::{BufRead, BufReader},
+ path::Path,
+};
+
+#[derive(Debug)]
+struct M {
+ a: P,
+ b: P,
+ p: P,
+}
+
+impl M {
+ fn from_lines(lines: &[String]) -> Self {
+ let a_line = &lines[0];
+ let b_line = &lines[1];
+ let p_line = &lines[2];
+
+ Self {
+ a: P {
+ x: a_line[&a_line.find("X").unwrap() + 2..a_line.find(",").unwrap()]
+ .parse()
+ .unwrap(),
+ y: a_line[&a_line.find("Y").unwrap() + 2..a_line.len()]
+ .parse()
+ .unwrap(),
+ },
+ b: P {
+ x: b_line[&b_line.find("X").unwrap() + 2..b_line.find(",").unwrap()]
+ .parse()
+ .unwrap(),
+ y: b_line[&b_line.find("Y").unwrap() + 2..b_line.len()]
+ .parse()
+ .unwrap(),
+ },
+ p: P {
+ x: p_line[&p_line.find("X").unwrap() + 2..p_line.find(",").unwrap()]
+ .parse::<usize>()
+ .unwrap()
+ + 10000000000000,
+ y: p_line[&p_line.find("Y").unwrap() + 2..p_line.len()]
+ .parse::<usize>()
+ .unwrap()
+ + 10000000000000,
+ },
+ }
+ }
+}
+
+#[derive(Debug)]
+struct P {
+ x: usize,
+ y: usize,
+}
+
+pub fn part_two(input: &Path) -> anyhow::Result<usize> {
+ let reader = BufReader::new(File::open(input)?);
+
+ let machines: Vec<M> = reader
+ .lines()
+ .filter_map(|l| {
+ let l = l.unwrap();
+ if !l.is_empty() {
+ Some(l)
+ } else {
+ None
+ }
+ })
+ .collect::<Vec<String>>()
+ .chunks(3)
+ .map(|l| -> M { M::from_lines(l) })
+ .collect();
+
+ let mut answer = 0;
+ for m in machines {
+ println!();
+ println!("{}x + {}y = {}", m.a.x, m.b.x, m.p.x);
+ println!("{}x + {}y = {}", m.a.y, m.b.y, m.p.y);
+ println!();
+
+ let b: i64 = (m.p.y as i64 * m.a.x as i64 - m.p.x as i64 * m.a.y as i64)
+ / (m.b.y as i64 * m.a.x as i64 - m.b.x as i64 * m.a.y as i64);
+ let a: i64 = (m.p.x as i64 - b * m.b.x as i64) / m.a.x as i64;
+ if m.a.x as i64 * a + m.b.x as i64 * b == m.p.x as i64
+ && m.a.y as i64 * a + m.b.y as i64 * b == m.p.y as i64
+ {
+ answer += a * 3 + b;
+ println!("yes");
+ }
+ }
+
+ Ok(answer as usize)
+}
M src/main.rs => src/main.rs +8 -0
@@ 6,6 6,7 @@ mod day1;
mod day10;
mod day11;
mod day12;
+mod day13;
mod day2;
mod day3;
mod day4;
@@ 71,6 72,10 @@ enum DayArgs {
#[arg(short)]
input: PathBuf,
},
+ Day13 {
+ #[arg(short)]
+ input: PathBuf,
+ },
}
fn main() -> anyhow::Result<()> {
@@ 113,6 118,9 @@ fn main() -> anyhow::Result<()> {
DayArgs::Day12 { input } => {
day12::solve(&input)?;
}
+ DayArgs::Day13 { input } => {
+ day13::solve(&input)?;
+ }
}
Ok(())