144 lines
4.4 KiB
TypeScript
144 lines
4.4 KiB
TypeScript
const sample = await Deno.readTextFile("sample.txt");
|
|
const input = await Deno.readTextFile("input.txt");
|
|
|
|
type Row<T> = T[];
|
|
type Matrix<T> = Row<T>[];
|
|
type Board = Matrix<number | undefined>;
|
|
|
|
const rotateMatrix = <T extends unknown>(matrix: Matrix<T>): Matrix<T> =>
|
|
matrix.map((_, index) => matrix.map((row) => row[index]));
|
|
|
|
const checkMatrixForEmptyRow = <T extends unknown>(
|
|
matrix: Matrix<T>
|
|
): boolean =>
|
|
Boolean(matrix.find((row) => row.every((value) => value === undefined)));
|
|
|
|
const filterMatrix = <T extends unknown>(
|
|
matrix: Matrix<T>,
|
|
number: number
|
|
): Matrix<T | undefined> =>
|
|
matrix.map((row) =>
|
|
row.map((value) => (value !== number ? value : undefined))
|
|
);
|
|
|
|
const parseNumbers = (data: string): number[] =>
|
|
data.split("\n")[0].split(",").map(parseFloat);
|
|
|
|
const parseBoards = (data: string): Board[] =>
|
|
data
|
|
.split("\n\n")
|
|
.slice(1)
|
|
.filter(Boolean)
|
|
.map((board) =>
|
|
board
|
|
.split("\n")
|
|
.filter(Boolean)
|
|
.map((line) => line.trim().split(/\ +/).map(parseFloat))
|
|
);
|
|
|
|
const solvePart1 = (data: string): number => {
|
|
const numbers = parseNumbers(data);
|
|
const boards = parseBoards(data);
|
|
|
|
return numbers.reduce(
|
|
({ boards, result }, number): { boards: Board[]; result: number } => {
|
|
if (result > -1) {
|
|
return { boards, result };
|
|
}
|
|
const filteredBoards = boards.map((board) => filterMatrix(board, number));
|
|
const matchingBoard = filteredBoards.find(checkMatrixForEmptyRow);
|
|
return {
|
|
boards: filteredBoards,
|
|
result: matchingBoard
|
|
? matchingBoard
|
|
.flatMap((row) => row.map((v) => v ?? 0))
|
|
.reduce((sum, value) => sum + value, 0) * number
|
|
: result,
|
|
};
|
|
},
|
|
{ boards: boards.concat(boards.map(rotateMatrix)), result: -1 }
|
|
).result;
|
|
};
|
|
|
|
console.log("Sample:", solvePart1(sample)); // 4512
|
|
console.log("Input", solvePart1(input)); // 38913
|
|
|
|
const solvePart2 = (data: string): number => {
|
|
const numbers = parseNumbers(data);
|
|
const parsedBoards = parseBoards(data);
|
|
|
|
const r = numbers
|
|
.reduce(
|
|
(boards, number, index) => [
|
|
...boards,
|
|
boards[index].map((variant) =>
|
|
variant.map((board) => filterMatrix(board, number))
|
|
),
|
|
],
|
|
[parsedBoards.map((board) => [board, rotateMatrix(board)])]
|
|
)
|
|
.map((boards, index) => ({ number: numbers[index - 1], boards: boards }));
|
|
|
|
const n2 = r.filter(({ boards }) =>
|
|
boards.flatMap((variant) => variant).find(checkMatrixForEmptyRow)
|
|
);
|
|
return console.log("n2", n2);
|
|
|
|
const n = r.find(({ boards }) => boards.find(checkMatrixForEmptyRow));
|
|
return console.log("r", r, n?.number);
|
|
|
|
return numbers.reduce(
|
|
(
|
|
{ boards, result },
|
|
number,
|
|
index
|
|
): { boards: Board[]; result: number } => {
|
|
if (result > -1) {
|
|
return { boards, result };
|
|
}
|
|
let filteredBoards = boards.map((board) => filterMatrix(board, number));
|
|
let matchingBoard = filteredBoards.find(checkMatrixForEmptyRow);
|
|
|
|
if (matchingBoard) {
|
|
if (filteredBoards.length === parsedBoards.length * 2) {
|
|
/* console.log("here", index, number, filteredBoards); */
|
|
filteredBoards = filteredBoards.filter((fb) => fb !== matchingBoard);
|
|
matchingBoard = undefined;
|
|
} else if (filteredBoards.length === parsedBoards.length * 2 - 1) {
|
|
filteredBoards = filteredBoards.filter((fb) => fb !== matchingBoard);
|
|
matchingBoard = filteredBoards[0];
|
|
console.log(
|
|
"here",
|
|
index,
|
|
number,
|
|
matchingBoard,
|
|
matchingBoard
|
|
.flatMap((row) => row.map((v) => v ?? 0))
|
|
.reduce((sum, value) => sum + value, 0)
|
|
);
|
|
}
|
|
}
|
|
/* const mb = filteredBoards.filter(checkMatrixForEmptyRow); */
|
|
/* console.log( */
|
|
/* "index, number", */
|
|
/* index, */
|
|
/* number, */
|
|
/* /* matchingBoard && filteredBoards.indexOf(matchingBoard) */
|
|
/* mb.length */
|
|
/* ); */
|
|
return {
|
|
boards: filteredBoards,
|
|
result: matchingBoard
|
|
? matchingBoard
|
|
.flatMap((row) => row.map((v) => v ?? 0))
|
|
.reduce((sum, value) => sum + value, 0) * number
|
|
: result,
|
|
};
|
|
},
|
|
{ boards: parsedBoards.concat(parsedBoards.map(rotateMatrix)), result: -1 }
|
|
).result;
|
|
};
|
|
|
|
console.log("Sample:", solvePart2(sample)); // 4512
|
|
/* console.log("Input", solvePart1(input)); // 38913 */
|