Skip to content

Instantly share code, notes, and snippets.

@RNGKing
Created December 2, 2023 19:34
Show Gist options
  • Save RNGKing/19500e0e4f9e70c2d81793947d123513 to your computer and use it in GitHub Desktop.
Save RNGKing/19500e0e4f9e70c2d81793947d123513 to your computer and use it in GitHub Desktop.
AoC in Gleam
import simplifile as file
import gleam/string
import gleam/regex.{type Regex}
import gleam/io
import gleam/list
import gleam/int
import gleam/bool
pub type Game {
Game(id: Int, red: Int, blue: Int, green: Int)
}
pub type GameRules {
GameRules(total_blue: Int, total_red: Int, total_green: Int)
}
pub type GameRegex {
GameRegex(
game_id: Regex,
blue_regex: Regex,
red_regex: Regex,
green_regex: Regex,
number_regex: Regex,
)
}
fn get_game_regex() -> GameRegex {
let assert Ok(game_id_regex) = regex.from_string("(Game [0-9]+)")
let assert Ok(blue_regex) = regex.from_string("([0-9]+ blue)")
let assert Ok(red_regex) = regex.from_string("([0-9]+ red)")
let assert Ok(green_regex) = regex.from_string("([0-9]+ green)")
let assert Ok(number_regex) = regex.from_string("([0-9]+)")
GameRegex(game_id_regex, blue_regex, red_regex, green_regex, number_regex)
}
fn parse_file_to_games(file_path: String) -> List(Game) {
let game_regex: GameRegex = get_game_regex()
let assert Ok(file_data) = file.read(file_path)
file_data
|> string.split("\n")
|> list.map(fn(line) { parse_string_to_game(line, game_regex) })
}
fn parse_string_to_game(line: String, gex: GameRegex) -> Game {
let game_id = sum_matches(line, gex.game_id, gex.number_regex)
let blue_count = sum_matches(line, gex.blue_regex, gex.number_regex)
let red_count = sum_matches(line, gex.red_regex, gex.number_regex)
let green_count = sum_matches(line, gex.green_regex, gex.number_regex)
Game(game_id, blue_count, red_count, green_count)
}
fn sum_matches(line: String, c_regex: Regex, number_regex: Regex) -> Int {
regex.scan(c_regex, line)
|> list.map(fn(match) { match.content })
|> list.map(fn(content) {
regex.scan(number_regex, content)
|> list.map(fn(match) { match.content })
|> list.map(fn(number) { parse_string_to_int(number) })
})
|> list.flatten
|> int.sum
}
fn parse_string_to_int(input: String) {
let assert Ok(output) = int.parse(input)
output
}
pub fn day_2_runner_test() {
part_one("./data/day_2/part_one_sample.dat")
part_one("./data/day_2/day_two_input.dat")
}
fn part_one(file_path: String) {
let game_rules = GameRules(14, 12, 13)
parse_file_to_games(file_path)
|> list.filter(fn(game) {
use <- bool.guard(when: game.blue >= game_rules.total_blue, return: False)
use <- bool.guard(when: game.red >= game_rules.total_red, return: False)
use <- bool.guard(when: game.green >= game_rules.total_green, return: False)
True
})
|> list.map(fn(game) { game.id })
|> int.sum
|> io.debug
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment