.
This commit is contained in:
21
2021/3.js
Normal file
21
2021/3.js
Normal file
@@ -0,0 +1,21 @@
|
||||
function day3(input, part2) {
|
||||
let g = Grid.fromStr(input)
|
||||
|
||||
if (!part2) {
|
||||
let gamma = g.getColumns().map((col) => col.mode())
|
||||
let epsilon = g.getColumns().map((col) => col.antimode())
|
||||
return parseInt(gamma.join``, 2) * parseInt(epsilon.join``, 2)
|
||||
} else {
|
||||
let oxy = g.getRows()
|
||||
let co2 = g.getRows()
|
||||
|
||||
for (let i = 0; i < g.width; i++) {
|
||||
let oxyBit = oxy.transpose()[i].mode((a, b) => a == 1 ? -1 : 1)
|
||||
let co2Bit = co2.transpose()[i].antimode((a, b) => a == 0 ? -1 : 1)
|
||||
oxy = oxy.filter((e) => e[i] == oxyBit)
|
||||
co2 = co2.filter((e) => e[i] == co2Bit)
|
||||
}
|
||||
|
||||
return parseInt(oxy[0].join``, 2) * parseInt(co2[0].join``, 2)
|
||||
}
|
||||
}
|
||||
34
2021/4.js
Normal file
34
2021/4.js
Normal file
@@ -0,0 +1,34 @@
|
||||
function day4(input, part2) {
|
||||
input = input.split("\n")
|
||||
|
||||
let seq = input.shift().split(",").num()
|
||||
let grids = input.splitOnElement("").filter((e) => e.length).map((grid) => Grid.fromStr(grid.map((line) => line.replace(/^ /, "")).join("\n"), /\s+/).mapMut((e) => [+e, false]))
|
||||
|
||||
let score
|
||||
|
||||
for (let num of seq) {
|
||||
for (let grid of grids) {
|
||||
if (grid.won) {
|
||||
continue
|
||||
}
|
||||
|
||||
let pt = grid.findIndex((e) => e[0] == num)
|
||||
|
||||
if (pt == Point.NONE) {
|
||||
continue
|
||||
}
|
||||
|
||||
grid.set(pt, [num, true])
|
||||
|
||||
if ([...grid.getRows(), ...grid.getColumns()].some((row) => row.every((e) => e[1]))) {
|
||||
grid.won = true
|
||||
|
||||
if (!score || part2) {
|
||||
score = grid.findAll((e) => !e[1]).map((e) => e[0]).sum() * num
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
return score
|
||||
}
|
||||
2
aoc
Executable file
2
aoc
Executable file
@@ -0,0 +1,2 @@
|
||||
#!/bin/bash
|
||||
NODE_INSPECT_RESUME_ON_START=1 node inspect out.js
|
||||
35
grid.js
35
grid.js
@@ -71,12 +71,45 @@ Grid = class Grid {
|
||||
}
|
||||
}
|
||||
|
||||
findAll(func) {
|
||||
getRows() {
|
||||
return this.data.copy()
|
||||
}
|
||||
|
||||
getColumns() {
|
||||
return this.data.transpose()
|
||||
}
|
||||
|
||||
findIndex(func) {
|
||||
for (let y = 0; y < this.height; y++) {
|
||||
for (let x = 0; x < this.width; x++) {
|
||||
let pt = new Point(x, y)
|
||||
if (func(this.get(pt), pt, this)) {
|
||||
return pt
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
return Point.NONE
|
||||
}
|
||||
|
||||
find(func) {
|
||||
return this.get(this.findIndex(func))
|
||||
}
|
||||
|
||||
findAllIndices(func) {
|
||||
let points = []
|
||||
this.forEach((e, pt, grid) => func(e, pt, grid) ? points.push(pt) : 0)
|
||||
return points
|
||||
}
|
||||
|
||||
findAll(func) {
|
||||
return this.findAllIndices(func).map((pt) => this.get(pt))
|
||||
}
|
||||
|
||||
indexOf(val) {
|
||||
return this.findIndex((e) => e == val)
|
||||
}
|
||||
|
||||
contains(pt) { return pt.x >= 0 && pt.x < this.width && pt.y >= 0 && pt.y < this.height }
|
||||
|
||||
getAdjNeighbors(pt) { return pt.getUnfilteredAdjNeighbors().filter((pt) => this.contains(pt)) }
|
||||
|
||||
97
out.js
97
out.js
@@ -232,6 +232,8 @@ Pt = Point = class Point {
|
||||
toString() { return this.x + "," + this.y }
|
||||
}
|
||||
|
||||
Point.NONE = new Point(null, null)
|
||||
|
||||
P = function P(...args) {
|
||||
return new Point(...args)
|
||||
}
|
||||
@@ -310,12 +312,45 @@ Grid = class Grid {
|
||||
}
|
||||
}
|
||||
|
||||
findAll(func) {
|
||||
getRows() {
|
||||
return this.data.copy()
|
||||
}
|
||||
|
||||
getColumns() {
|
||||
return this.data.transpose()
|
||||
}
|
||||
|
||||
findIndex(func) {
|
||||
for (let y = 0; y < this.height; y++) {
|
||||
for (let x = 0; x < this.width; x++) {
|
||||
let pt = new Point(x, y)
|
||||
if (func(this.get(pt), pt, this)) {
|
||||
return pt
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
return Point.NONE
|
||||
}
|
||||
|
||||
find(func) {
|
||||
return this.get(this.findIndex(func))
|
||||
}
|
||||
|
||||
findAllIndices(func) {
|
||||
let points = []
|
||||
this.forEach((e, pt, grid) => func(e, pt, grid) ? points.push(pt) : 0)
|
||||
return points
|
||||
}
|
||||
|
||||
findAll(func) {
|
||||
return this.findAllIndices(func).map((pt) => this.get(pt))
|
||||
}
|
||||
|
||||
indexOf(val) {
|
||||
return this.findIndex((e) => e == val)
|
||||
}
|
||||
|
||||
contains(pt) { return pt.x >= 0 && pt.x < this.width && pt.y >= 0 && pt.y < this.height }
|
||||
|
||||
getAdjNeighbors(pt) { return pt.getUnfilteredAdjNeighbors().filter((pt) => this.contains(pt)) }
|
||||
@@ -674,6 +709,28 @@ load = function load() {
|
||||
},
|
||||
configurable: true
|
||||
},
|
||||
truthy: {
|
||||
value: function() {
|
||||
return this.filter((e) => e)
|
||||
},
|
||||
configurable: true
|
||||
},
|
||||
splitOnElement: {
|
||||
value: function(sep) {
|
||||
let arr = [[]]
|
||||
|
||||
for (let i = 0; i < this.length; i++) {
|
||||
if (this[i] == sep) {
|
||||
arr.push([])
|
||||
} else {
|
||||
arr[arr.length - 1].push(this[i])
|
||||
}
|
||||
}
|
||||
|
||||
return arr
|
||||
},
|
||||
configurable: true
|
||||
},
|
||||
copy: {
|
||||
value: function() {
|
||||
return this.slice()
|
||||
@@ -687,7 +744,7 @@ load = function load() {
|
||||
configurable: true
|
||||
},
|
||||
sum: {
|
||||
value: function(val) {
|
||||
value: function(val = 0) {
|
||||
return this.reduce((a, b) => a + b, val)
|
||||
},
|
||||
configurable: true
|
||||
@@ -776,15 +833,17 @@ load = function load() {
|
||||
},
|
||||
minIndex: {
|
||||
value: function(fn = (e) => e, tiebreak) {
|
||||
let min = Infinity
|
||||
let minval = Infinity
|
||||
let min
|
||||
let idx
|
||||
|
||||
for (let i = 0; i < this.length; i++) {
|
||||
let val = fn(this[i])
|
||||
|
||||
if (min > val ||
|
||||
(min == val && tiebreak && tiebreak(min, val, idx, i) > 0)) {
|
||||
min = val
|
||||
if (minval > val ||
|
||||
(minval == val && tiebreak && tiebreak(min, this[i], idx, i) > 0)) {
|
||||
minval = val
|
||||
min = this[i]
|
||||
idx = i
|
||||
}
|
||||
}
|
||||
@@ -801,15 +860,17 @@ load = function load() {
|
||||
},
|
||||
maxIndex: {
|
||||
value: function(fn = (e) => e, tiebreak) {
|
||||
let max = -Infinity
|
||||
let maxval = -Infinity
|
||||
let max
|
||||
let idx
|
||||
|
||||
for (let i = 0; i < this.length; i++) {
|
||||
let val = fn(this[i])
|
||||
|
||||
if (max < val ||
|
||||
(max == val && tiebreak && tiebreak(max, val, idx, i) > 0)) {
|
||||
max = val
|
||||
if (maxval < val ||
|
||||
(maxval == val && tiebreak && tiebreak(max, this[i], idx, i) > 0)) {
|
||||
maxval = val
|
||||
max = this[i]
|
||||
idx = i
|
||||
}
|
||||
}
|
||||
@@ -851,6 +912,22 @@ load = function load() {
|
||||
})
|
||||
|
||||
Object.defineProperties(PointArray.prototype, {
|
||||
splitOnElement: {
|
||||
value: function(sep) {
|
||||
let arr = [[]]
|
||||
|
||||
for (let i = 0; i < this.length; i++) {
|
||||
if (this[i].equals(sep)) {
|
||||
arr.push([])
|
||||
} else {
|
||||
arr[arr.length - 1].push(this[i])
|
||||
}
|
||||
}
|
||||
|
||||
return arr
|
||||
},
|
||||
configurable: true
|
||||
},
|
||||
sort: {
|
||||
value: function(func = (a, b) => a.readingOrderCompare(b)) {
|
||||
return Array.prototype.sort.apply(this, func)
|
||||
|
||||
60
proto.js
60
proto.js
@@ -54,6 +54,28 @@ load = function load() {
|
||||
},
|
||||
configurable: true
|
||||
},
|
||||
truthy: {
|
||||
value: function() {
|
||||
return this.filter((e) => e)
|
||||
},
|
||||
configurable: true
|
||||
},
|
||||
splitOnElement: {
|
||||
value: function(sep) {
|
||||
let arr = [[]]
|
||||
|
||||
for (let i = 0; i < this.length; i++) {
|
||||
if (this[i] == sep) {
|
||||
arr.push([])
|
||||
} else {
|
||||
arr[arr.length - 1].push(this[i])
|
||||
}
|
||||
}
|
||||
|
||||
return arr
|
||||
},
|
||||
configurable: true
|
||||
},
|
||||
copy: {
|
||||
value: function() {
|
||||
return this.slice()
|
||||
@@ -67,7 +89,7 @@ load = function load() {
|
||||
configurable: true
|
||||
},
|
||||
sum: {
|
||||
value: function(val) {
|
||||
value: function(val = 0) {
|
||||
return this.reduce((a, b) => a + b, val)
|
||||
},
|
||||
configurable: true
|
||||
@@ -156,15 +178,17 @@ load = function load() {
|
||||
},
|
||||
minIndex: {
|
||||
value: function(fn = (e) => e, tiebreak) {
|
||||
let min = Infinity
|
||||
let minval = Infinity
|
||||
let min
|
||||
let idx
|
||||
|
||||
for (let i = 0; i < this.length; i++) {
|
||||
let val = fn(this[i])
|
||||
|
||||
if (min > val ||
|
||||
(min == val && tiebreak && tiebreak(min, val, idx, i) > 0)) {
|
||||
min = val
|
||||
if (minval > val ||
|
||||
(minval == val && tiebreak && tiebreak(min, this[i], idx, i) > 0)) {
|
||||
minval = val
|
||||
min = this[i]
|
||||
idx = i
|
||||
}
|
||||
}
|
||||
@@ -181,15 +205,17 @@ load = function load() {
|
||||
},
|
||||
maxIndex: {
|
||||
value: function(fn = (e) => e, tiebreak) {
|
||||
let max = -Infinity
|
||||
let maxval = -Infinity
|
||||
let max
|
||||
let idx
|
||||
|
||||
for (let i = 0; i < this.length; i++) {
|
||||
let val = fn(this[i])
|
||||
|
||||
if (max < val ||
|
||||
(max == val && tiebreak && tiebreak(max, val, idx, i) > 0)) {
|
||||
max = val
|
||||
if (maxval < val ||
|
||||
(maxval == val && tiebreak && tiebreak(max, this[i], idx, i) > 0)) {
|
||||
maxval = val
|
||||
max = this[i]
|
||||
idx = i
|
||||
}
|
||||
}
|
||||
@@ -231,6 +257,22 @@ load = function load() {
|
||||
})
|
||||
|
||||
Object.defineProperties(PointArray.prototype, {
|
||||
splitOnElement: {
|
||||
value: function(sep) {
|
||||
let arr = [[]]
|
||||
|
||||
for (let i = 0; i < this.length; i++) {
|
||||
if (this[i].equals(sep)) {
|
||||
arr.push([])
|
||||
} else {
|
||||
arr[arr.length - 1].push(this[i])
|
||||
}
|
||||
}
|
||||
|
||||
return arr
|
||||
},
|
||||
configurable: true
|
||||
},
|
||||
sort: {
|
||||
value: function(func = (a, b) => a.readingOrderCompare(b)) {
|
||||
return Array.prototype.sort.apply(this, func)
|
||||
|
||||
Reference in New Issue
Block a user