main
Yanick Champoux 2021-12-05 11:44:39 -05:00
parent 703990eedc
commit 902e83b8ba
7 changed files with 139 additions and 0 deletions

8
2021/02/part1.mjs Normal file
View File

@ -0,0 +1,8 @@
import fp from "lodash/fp.js";
export const solution = fp.flow([
fp.groupBy(0),
fp.mapValues(fp.map(fp.get(1))),
fp.mapValues(fp.sum),
({ forward, up, down }) => forward * (down - up),
]);

35
2021/02/part1.pm Normal file
View File

@ -0,0 +1,35 @@
package part1;
use 5.34.0;
use warnings;
use experimental 'signatures';
use List::AllUtils qw/sum/;
sub group_by(@lines) {
my %grouped = ();
for my $line (@lines) {
my( $action, $move ) = split ' ', $line;
$grouped{$action} //= [];
push $grouped{$action}->@*, $move;
}
return %grouped;
}
sub solution(@lines) {
my %grouped = group_by(@lines);
for my $v (values %grouped) {
$v = sum @$v;
}
my $depth = $grouped{down} - $grouped{up};
my $forward = $grouped{forward};
return $depth * $forward;
}
1;

18
2021/02/part2.mjs Normal file
View File

@ -0,0 +1,18 @@
import fp from "lodash/fp.js";
import u from "updeep";
const update = (action, value) =>
action === "down" ? u({ aim: fp.add(value) })
: action === "up" ? u({ aim: fp.add(-value) })
: u((state) =>
u({ x: fp.add(value), depth: fp.add(value * state.aim) }, state)
);
export function solution(lines) {
const { x, depth } = lines.reduce(
(accum, line) => update(...line)(accum),
{ depth: 0, aim: 0, x: 0 }
);
return x * depth;
}

27
2021/02/part2.pm Normal file
View File

@ -0,0 +1,27 @@
package part2;
use 5.34.0;
use experimental qw/ signatures switch/;
sub solution(@lines) {
my( $depth, $aim, $x );
for my $line ( @lines ) {
my( $action, $value ) = split ' ', $line;
given($action) {
$aim+=$value when 'down';
$aim-=$value when 'up';
when( 'forward' ) {
$x += $value;
$depth += $aim * $value;
}
}
}
return $x * $depth;
}
1;

6
2021/02/sample Normal file
View File

@ -0,0 +1,6 @@
forward 5
down 5
forward 8
up 3
down 8
forward 2

25
2021/02/test.mjs Normal file
View File

@ -0,0 +1,25 @@
import tap from "tap";
import fs from "fs-extra";
import * as part1 from "./part1.mjs";
import * as part2 from "./part2.mjs";
const processFile = async (f) =>
fs
.readFile(f, "utf8")
.then((x) => x.split("\n"))
.then((lines) => lines.map((l) => l.split(" ")))
.then((lines) => lines.filter( ([action]) => action ).map((l) => [l[0], parseInt(l[1])]));
const sample = processFile("sample");
const input = processFile("input");
tap.test("part1", async (t) => {
t.equal(part1.solution(await sample), 150);
t.equal(part1.solution(await input), 2091984);
});
tap.test("part2", async (t) => {
t.equal(part2.solution(await sample), 900);
t.equal(part2.solution(await input), 2086261056);
});

20
2021/02/test.t Normal file
View File

@ -0,0 +1,20 @@
use 5.34.0;
use Test2::V0;
use Path::Tiny;
require './part1.pm';
require './part2.pm';
my @sample = path('sample')->lines;
my @input = path('input')->lines;
subtest part1 => sub {
is part1::solution(@sample) => 150;
is part1::solution(@input) => 2091984;
};
subtest part2 => sub {
is part2::solution(@sample ) => 900;
is part2::solution(@input) => 2086261056;
};