diff --git a/2024/05/2024-05.run.xml b/2024/05/2024-05.run.xml new file mode 100644 index 0000000..39a5d83 --- /dev/null +++ b/2024/05/2024-05.run.xml @@ -0,0 +1,7 @@ + + + + \ No newline at end of file diff --git a/2024/05/index.test.ts b/2024/05/index.test.ts new file mode 100644 index 0000000..e3d1596 --- /dev/null +++ b/2024/05/index.test.ts @@ -0,0 +1,39 @@ +import { describe, expect, it } from 'bun:test'; +import { solveFirst, solveSecond } from './index.ts'; + +describe('2024-05', () => { + const testInput = `47|53 +97|13 +97|61 +97|47 +75|29 +61|13 +75|53 +29|13 +97|29 +53|29 +61|53 +97|53 +61|29 +47|13 +75|47 +97|75 +47|61 +75|61 +47|29 +75|13 +53|13 + +75,47,61,53,29 +97,61,53,29,13 +75,29,13 +75,97,47,61,53 +61,13,29 +97,13,75,29,47`; + it('first', () => { + expect(solveFirst(testInput)).toBe(143); + }); + it('second', () => { + expect(solveSecond(testInput)).toBe(123); + }); +}); diff --git a/2024/05/index.ts b/2024/05/index.ts new file mode 100644 index 0000000..3971e35 --- /dev/null +++ b/2024/05/index.ts @@ -0,0 +1,53 @@ +import { getMiddleElement, sumArray } from '../../utils/array.ts'; + +export function solveFirst(input: string): number { + const { order, rows } = parseInput(input); + + const filteredRows = rows.filter((r) => isInOrder(r, order)); + + const middles = filteredRows.map((r) => r[Math.floor(r.length / 2)]); + + return sumArray(middles); +} + +function parseInput(input: string) { + const order = Array.from( + input.matchAll(/^(\d*)\|(\d*)$/gm), + (m) => [Number(m[1]), Number(m[2])] as [number, number] + ); + const rows = Array.from(input.matchAll(/^(\d+,?)+$/gm), (m) => + m[0].split(',').map((n) => Number(n)) + ); + return { order, rows }; +} + +function isInOrder(numbers: number[], order: [number, number][]) { + return numbers.every((number, index) => { + return order + .filter((o) => o[0] === number) + .every((o) => numbers.indexOf(o[1]) > index || numbers.indexOf(o[1]) < 0); + }); +} + +export function solveSecond(input: string): number { + const { order, rows } = parseInput(input); + + const filteredRows = rows.filter((r) => !isInOrder(r, order)); + + const sorted = filteredRows.map((r) => + r.toSorted((a, b) => { + // Find [a,b] meaning a should be before b = -1 + return order.findIndex((o) => o[0] === a && o[1] === b) >= 0 + ? -1 + : // Find [b,a] meaning a should be after b = 1 + order.findIndex((o) => o[1] === a && o[0] === b) >= 0 + ? 1 + : // No order specified, just ignore = 0 + 0; + }) + ); + + const middles = sorted.map(getMiddleElement); + + return sumArray(middles); +} diff --git a/2024/05/run.ts b/2024/05/run.ts new file mode 100644 index 0000000..88783cd --- /dev/null +++ b/2024/05/run.ts @@ -0,0 +1,12 @@ +import { join } from 'path'; +import { solveFirst, solveSecond } from './index.ts'; + +const input = await Bun.file(join(__dirname, 'input.txt')).text(); + +const firstAnswer = solveFirst(input); + +console.log(firstAnswer); + +const secondAnswer = solveSecond(input); + +console.log(secondAnswer);