This commit is contained in:
Rupus Reinefjord 2024-12-03 18:47:31 +01:00
parent ace0f38373
commit 1b1e321264
5 changed files with 141 additions and 0 deletions

4
2024/day03/.gitignore vendored Normal file
View file

@ -0,0 +1,4 @@
*.beam
*.ez
/build
erl_crash.dump

21
2024/day03/gleam.toml Normal file
View file

@ -0,0 +1,21 @@
name = "day03"
version = "1.0.0"
# Fill out these fields if you intend to generate HTML documentation or publish
# your project to the Hex package manager.
#
# description = ""
# licences = ["Apache-2.0"]
# repository = { type = "github", user = "", repo = "" }
# links = [{ title = "Website", href = "" }]
#
# For a full reference of all the available options, you can have a look at
# https://gleam.run/writing-gleam/gleam-toml/.
[dependencies]
gleam_stdlib = ">= 0.34.0 and < 2.0.0"
gleam_yielder = ">= 1.1.0 and < 2.0.0"
gleam_regexp = ">= 1.0.0 and < 2.0.0"
[dev-dependencies]
gleeunit = ">= 1.0.0 and < 2.0.0"

15
2024/day03/manifest.toml Normal file
View file

@ -0,0 +1,15 @@
# This file was generated by Gleam
# You typically do not need to edit this file
packages = [
{ name = "gleam_regexp", version = "1.0.0", build_tools = ["gleam"], requirements = ["gleam_stdlib"], otp_app = "gleam_regexp", source = "hex", outer_checksum = "A3655FDD288571E90EE9C4009B719FEF59FA16AFCDF3952A76A125AF23CF1592" },
{ name = "gleam_stdlib", version = "0.45.0", build_tools = ["gleam"], requirements = [], otp_app = "gleam_stdlib", source = "hex", outer_checksum = "206FCE1A76974AECFC55AEBCD0217D59EDE4E408C016E2CFCCC8FF51278F186E" },
{ name = "gleam_yielder", version = "1.1.0", build_tools = ["gleam"], requirements = ["gleam_stdlib"], otp_app = "gleam_yielder", source = "hex", outer_checksum = "8E4E4ECFA7982859F430C57F549200C7749823C106759F4A19A78AEA6687717A" },
{ name = "gleeunit", version = "1.2.0", build_tools = ["gleam"], requirements = ["gleam_stdlib"], otp_app = "gleeunit", source = "hex", outer_checksum = "F7A7228925D3EE7D0813C922E062BFD6D7E9310F0BEE585D3A42F3307E3CFD13" },
]
[requirements]
gleam_regexp = { version = ">= 1.0.0 and < 2.0.0" }
gleam_stdlib = { version = ">= 0.34.0 and < 2.0.0" }
gleam_yielder = { version = ">= 1.1.0 and < 2.0.0" }
gleeunit = { version = ">= 1.0.0 and < 2.0.0" }

View file

@ -0,0 +1,77 @@
import gleam/int
import gleam/io
import gleam/list
import gleam/option.{None, Some}
import gleam/regexp
import gleam/string
import gleam/yielder
import stdin.{stdin}
pub fn main() {
let memory =
stdin()
|> yielder.to_list
|> string.concat
part1(memory) |> int.to_string |> io.println
part2(memory) |> int.to_string |> io.println
}
fn part1(memory: String) -> Int {
let assert Ok(re) =
regexp.compile(
"mul\\((\\d{1,3}),(\\d{1,3})\\)",
regexp.Options(case_insensitive: False, multi_line: True),
)
regexp.scan(re, memory)
|> list.map(fn(m) {
list.map(m.submatches, fn(s) {
case s {
Some(n) -> int.parse(n)
None -> Error(Nil)
}
})
})
|> list.map(fn(x) {
let assert [Ok(a), Ok(b)] = x
a * b
})
|> int.sum
}
fn part2(memory: String) {
let assert Ok(re) =
regexp.compile(
"do\\(\\)|don't\\(\\)|mul\\((\\d{1,3}),(\\d{1,3})\\)",
regexp.Options(case_insensitive: False, multi_line: True),
)
regexp.scan(re, memory)
|> do(True)
|> list.map(fn(x) {
let assert Ok(a) = int.parse(x.0)
let assert Ok(b) = int.parse(x.1)
a * b
})
|> int.sum
}
fn do(matches: List(regexp.Match), enabled: Bool) -> List(#(String, String)) {
case matches {
[match, ..rest] ->
case match.content {
"do()" -> do(rest, True)
"don't()" -> do(rest, False)
_ ->
case enabled {
True ->
case match.submatches {
[Some(a), Some(b)] ->
list.flatten([[#(a, b)], do(rest, enabled)])
_ -> panic as "Invalid submatches!"
}
False -> do(rest, enabled)
}
}
[] -> []
}
}

View file

@ -0,0 +1,24 @@
import gleam/dynamic
import gleam/result
import gleam/yielder
@external(erlang, "io", "get_line")
fn ffi_read_line(prompt: String) -> dynamic.Dynamic
fn read_line() -> Result(String, Nil) {
ffi_read_line("")
|> dynamic.from()
|> dynamic.string()
|> result.replace_error(Nil)
}
fn assert_upwrap(res: Result(a, _)) -> a {
let assert Ok(a) = res
a
}
pub fn stdin() -> yielder.Yielder(String) {
yielder.repeatedly(read_line)
|> yielder.take_while(result.is_ok)
|> yielder.map(assert_upwrap)
}