AOC2022/src/10_Cathode-RayTube/Cathode-RayTube.ts
2022-12-10 13:28:14 +01:00

61 lines
1.6 KiB
TypeScript

const input = Deno.readTextFileSync('./input.txt').trimEnd().split('\n');
type State = { register: number; valX: number };
/**
* Returns Instruction list
* n=0: noop
* n!=0: addx n
*/
function getInstructions(input: Array<string>): Array<number> {
const instructions: Array<number> = [];
for (const line of input) {
const [type, value] = line.split(' ');
if (type === 'noop') {
instructions.push(0);
} else instructions.push(parseInt(value));
}
return instructions;
}
function getScreenChar(state: State): string {
let screenPos = (state.register % 40);
// Fix line wrap caused by modulo (as index starts at 1)
if (screenPos === 0) screenPos = 40;
if (screenPos >= state.valX && screenPos <= state.valX + 2) {
return '#';
}
return '.';
}
function* runCycles(instructions: Array<number>, register = 0, valX = 1): Generator<State> {
for (const instruction of instructions) {
register++;
yield { register: register, valX: valX };
if (instruction === 0) continue;
register++;
yield { register: register, valX: valX };
valX += instruction;
}
}
const instructions = getInstructions(input);
const checkCycles = new Set([20, 60, 100, 140, 180, 220]);
let p1 = 0;
let screen = '';
for (const state of runCycles(instructions)) {
// Relevant cycles Solution Part 1
if (checkCycles.has(state.register)) {
p1 += state.register * state.valX;
}
// Generate screen char for Part 2
screen += getScreenChar(state);
}
console.log('Solution Part 1:', p1);
console.log('Solution Part 2:');
for (const line of screen.match(/.{40}/g)!) {
console.log(line);
}