Day 8
This commit is contained in:
parent
d1c0ec56de
commit
703d330980
3 changed files with 120 additions and 1 deletions
|
@ -1,5 +1,5 @@
|
||||||
use aoc_runner_derive::{aoc, aoc_generator};
|
use aoc_runner_derive::{aoc, aoc_generator};
|
||||||
use std::collections::{HashMap, HashSet, VecDeque};
|
use std::collections::{HashMap, VecDeque};
|
||||||
|
|
||||||
pub struct Data {
|
pub struct Data {
|
||||||
fwd: HashMap<String, Vec<(usize, String)>>,
|
fwd: HashMap<String, Vec<(usize, String)>>,
|
||||||
|
|
118
src/day8.rs
Normal file
118
src/day8.rs
Normal file
|
@ -0,0 +1,118 @@
|
||||||
|
use aoc_runner_derive::{aoc, aoc_generator};
|
||||||
|
use std::collections::HashSet;
|
||||||
|
|
||||||
|
#[derive(Debug, Ord, PartialOrd, Eq, PartialEq, Clone)]
|
||||||
|
pub enum Inst {
|
||||||
|
Acc { value: i64 },
|
||||||
|
Jmp { offset: i64 },
|
||||||
|
Nop { unused: i64 },
|
||||||
|
}
|
||||||
|
#[derive(Debug, Ord, PartialOrd, Eq, PartialEq)]
|
||||||
|
pub struct CPU {
|
||||||
|
ip: usize,
|
||||||
|
program: Vec<Inst>,
|
||||||
|
acc: i64,
|
||||||
|
}
|
||||||
|
|
||||||
|
impl From<&str> for Inst {
|
||||||
|
fn from(inst: &str) -> Self {
|
||||||
|
let mut inst = inst.split_whitespace();
|
||||||
|
let (inst, arg) = (
|
||||||
|
inst.next().unwrap(),
|
||||||
|
inst.next().map(|v| v.parse::<i64>().unwrap()),
|
||||||
|
);
|
||||||
|
match inst {
|
||||||
|
"jmp" => Inst::Jmp {
|
||||||
|
offset: arg.unwrap(),
|
||||||
|
},
|
||||||
|
"acc" => Inst::Acc {
|
||||||
|
value: arg.unwrap(),
|
||||||
|
},
|
||||||
|
"nop" => Inst::Nop {
|
||||||
|
unused: arg.unwrap(),
|
||||||
|
},
|
||||||
|
other => panic!("Invalid instruction: {}", other),
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
impl CPU {
|
||||||
|
fn new(pgm: &Vec<Inst>) -> Self {
|
||||||
|
Self {
|
||||||
|
ip: 0,
|
||||||
|
program: pgm.clone(),
|
||||||
|
acc: 0,
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
fn flip(&mut self, idx: usize) {
|
||||||
|
if let Some(new_inst) = match &self.program[idx] {
|
||||||
|
Inst::Jmp { offset } => Some(Inst::Nop { unused: *offset }),
|
||||||
|
Inst::Nop { unused } => Some(Inst::Jmp { offset: *unused }),
|
||||||
|
_ => None,
|
||||||
|
} {
|
||||||
|
self.program[idx] = new_inst;
|
||||||
|
};
|
||||||
|
}
|
||||||
|
|
||||||
|
fn step(&mut self) -> bool {
|
||||||
|
// println!("{}: {:?} [Acc: {}]",self.ip,inst, self.acc);
|
||||||
|
match self.program.get(self.ip) {
|
||||||
|
Some(Inst::Acc { value }) => {
|
||||||
|
self.acc += value;
|
||||||
|
}
|
||||||
|
Some(Inst::Jmp { offset }) => {
|
||||||
|
self.ip = ((self.ip as i64) + (offset - 1)) as usize;
|
||||||
|
}
|
||||||
|
Some(Inst::Nop { .. }) => (),
|
||||||
|
None => {
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
self.ip += 1;
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
#[aoc_generator(day8)]
|
||||||
|
pub fn input_generator(input: &str) -> Vec<Inst> {
|
||||||
|
input.trim().lines().map(|l| Inst::from(l.trim())).collect()
|
||||||
|
}
|
||||||
|
|
||||||
|
#[aoc(day8, part1)]
|
||||||
|
pub fn solve_part1(input: &Vec<Inst>) -> usize {
|
||||||
|
let mut seen = HashSet::new();
|
||||||
|
let mut cpu = CPU::new(input);
|
||||||
|
loop {
|
||||||
|
seen.insert(cpu.ip);
|
||||||
|
cpu.step();
|
||||||
|
if seen.contains(&cpu.ip) {
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return cpu.acc as usize;
|
||||||
|
}
|
||||||
|
|
||||||
|
#[aoc(day8, part2)]
|
||||||
|
pub fn solve_part2(input: &Vec<Inst>) -> usize {
|
||||||
|
for (idx, inst) in input.iter().enumerate() {
|
||||||
|
match inst {
|
||||||
|
Inst::Nop { .. } | Inst::Jmp { .. } => {
|
||||||
|
let mut seen = HashSet::new();
|
||||||
|
let mut cpu = CPU::new(input);
|
||||||
|
cpu.flip(idx);
|
||||||
|
loop {
|
||||||
|
seen.insert(cpu.ip);
|
||||||
|
if !cpu.step() {
|
||||||
|
return cpu.acc as usize;
|
||||||
|
};
|
||||||
|
if seen.contains(&cpu.ip) {
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
_ => (),
|
||||||
|
}
|
||||||
|
}
|
||||||
|
panic!("Failed to solve part 2");
|
||||||
|
}
|
|
@ -6,4 +6,5 @@ pub mod day4;
|
||||||
pub mod day5;
|
pub mod day5;
|
||||||
pub mod day6;
|
pub mod day6;
|
||||||
pub mod day7;
|
pub mod day7;
|
||||||
|
pub mod day8;
|
||||||
aoc_lib! { year = 2020 }
|
aoc_lib! { year = 2020 }
|
||||||
|
|
Loading…
Reference in a new issue