diff options
| author | Alexandre Jesus <adbjesus@gmail.com> | 2025-12-06 18:40:45 +0000 |
|---|---|---|
| committer | Alexandre Jesus <adbjesus@gmail.com> | 2025-12-06 18:40:45 +0000 |
| commit | 5f4461fe96d07bef69cb59f5ce7182848340a951 (patch) | |
| tree | 143fd15801757b1bdba69fd983f2e1aa77bef779 | |
| parent | ad818259ba31a98a3c00326894ebd71bbbde4667 (diff) | |
| download | aoc2025-5f4461fe96d07bef69cb59f5ce7182848340a951.tar.gz aoc2025-5f4461fe96d07bef69cb59f5ce7182848340a951.zip | |
Day 6
| -rw-r--r-- | bin/main.ml | 2 | ||||
| m--------- | data | 0 | ||||
| -rw-r--r-- | lib/day06.ml | 66 |
3 files changed, 68 insertions, 0 deletions
diff --git a/bin/main.ml b/bin/main.ml index b5d7303..ebde0e3 100644 --- a/bin/main.ml +++ b/bin/main.ml @@ -36,6 +36,8 @@ let day_part_fn day part = | 4, 2 -> Day04.part2 | 5, 1 -> Day05.part1 | 5, 2 -> Day05.part2 + | 6, 1 -> Day06.part1 + | 6, 2 -> Day06.part2 | _ -> failwith (Format.sprintf "Day %d, part %d, has not yet been implemented\n" day diff --git a/data b/data -Subproject 464e5178039496d1ed565669da7d13c14416a7d +Subproject fade3292f33ea16f360782f0c55d3ce2b72ea5a diff --git a/lib/day06.ml b/lib/day06.ml new file mode 100644 index 0000000..7457c6d --- /dev/null +++ b/lib/day06.ml @@ -0,0 +1,66 @@ +(* + * SPDX-FileCopyrightText: Copyright 2025 Alexandre Jesus <https://adbjesus.com> + * + * SPDX-License-Identifier: GPL-3.0-or-later + *) + +let part1 ch = + let ops, nums = + In_channel.input_all ch + |> String.trim + |> String.split_on_char '\n' + |> List.map (String.split_on_char ' ') + |> List.map (List.filter (( <> ) "")) + |> List.rev + |> fun l -> (List.hd l, List.map (List.map int_of_string) (List.tl l)) + in + List.fold_left + (fun acc l -> List.map2 (fun (r, op) v -> (op r v, op)) acc l) + (List.map (fun o -> if o = "*" then (1, ( * )) else (0, ( + ))) ops) + nums + |> List.map fst + |> List.fold_left ( + ) 0 + |> Printf.printf "%d\n" + +let part2 ch = + (* another option would be to tranpose the numbers, but I wanted to avoid it *) + let parse_nums lines = + let czero = Char.code '0' in + let parse_digit c = if c = ' ' then None else Some (Char.code c - czero) in + let rec fn nums line = + match (nums, Seq.uncons line) with + | [], None -> [] + | nums, None -> nums + | [], Some (v, tv) -> parse_digit v :: fn [] tv + | n :: tn, Some (v, tv) -> ( + match (n, parse_digit v) with + | Some n, Some v -> Some ((n * 10) + v) :: fn tn tv + | Some n, None -> Some n :: fn tn tv + | None, Some v -> Some v :: fn tn tv + | None, None -> None :: fn tn tv) + in + List.fold_left (fun acc line -> fn acc (String.to_seq line)) [] lines + |> List.fold_left + (fun acc n -> + match n with + | None -> [] :: acc + | Some n -> (n :: List.hd acc) :: List.tl acc) + [ [] ] + |> List.filter (( <> ) []) + |> List.rev + in + let parse_ops line = + String.split_on_char ' ' line |> List.filter (( <> ) "") + in + let data = In_channel.input_all ch in + let lines = data |> String.split_on_char '\n' |> List.filter (( <> ) "") in + let rlines = List.rev lines in + let ops = parse_ops (List.hd rlines) in + let nums = parse_nums (List.rev (List.tl rlines)) in + List.map2 + (fun op nums -> + if op = "*" then List.fold_left ( * ) 1 nums + else List.fold_left ( + ) 0 nums) + ops nums + |> List.fold_left ( + ) 0 + |> Printf.printf "%d\n" |
