Line data Source code
1 : #include "PuzzleImpl.h"
2 : #include "Regex.h"
3 :
4 : #include <re2/re2.h>
5 :
6 : #include <ranges>
7 :
8 : namespace {
9 :
10 23 : uint64_t parseMults(std::string_view const s) {
11 23 : static FindAndConsume<uint64_t, uint64_t> fac(R"(mul\((\d{1,3}),(\d{1,3})\))");
12 :
13 1087 : auto tupleProduct = [](auto const &t) { return get<0>(t) * get<1>(t); };
14 :
15 23 : return std::ranges::fold_left(fac(s) | std::views::transform(tupleProduct), uint64_t(0),
16 23 : std::plus{});
17 23 : }
18 :
19 : } // namespace
20 :
21 1 : template <> size_t part1<2024, 3>(std::string_view const input) { return parseMults(input); }
22 :
23 1 : template <> size_t part2<2024, 3>(std::string_view const input) {
24 1 : std::string_view s = input;
25 1 : uint64_t result = 0;
26 :
27 1 : RE2::Options o;
28 1 : o.set_dot_nl(true);
29 1 : RE2 dontPattern(R"((.*?)don't\(\))", o);
30 1 : RE2 doPattern(R"(do\(\))");
31 :
32 1 : bool enabled = true;
33 23 : while (enabled) {
34 22 : std::string_view enabledMults;
35 22 : if (RE2::Consume(&s, dontPattern, &enabledMults)) {
36 21 : result += parseMults(enabledMults);
37 21 : enabled = RE2::FindAndConsume(&s, doPattern);
38 21 : } else {
39 1 : result += parseMults(s);
40 1 : enabled = false;
41 1 : }
42 22 : }
43 :
44 1 : return result;
45 1 : }
|