advent2024

Advent of Code 2024
git clone git://bsandro.tech/advent2024
Log | Files | Refs

main.cpp (2733B)


      1 #include <iostream>
      2 #include <filesystem>
      3 #include <fstream>
      4 #include <vector>
      5 #include <cstring>
      6 #include <cstdio>
      7 #include <tuple>
      8 #include <algorithm>
      9 #include <thread>
     10 #include "utils.hpp"
     11 
     12 struct Vec2 {
     13     int x;
     14     int y;
     15     void fromStr(const std::string &s) {
     16         [[ maybe_unused ]] char btn;
     17         std::sscanf(s.c_str(), "Button %c: X+%d, Y+%d", &btn, &x, &y);
     18     }
     19 };
     20 
     21 struct Machine {
     22     Vec2 btnA;
     23     Vec2 btnB;
     24     Vec2 prize;
     25     void setPrize(const std::string &s) {
     26         std::sscanf(s.c_str(), "Prize: X=%d, Y=%d", &prize.x, &prize.y);
     27     }
     28     void print() const {
     29         std::printf("A(%d,%d), B(%d,%d), prize at (%d,%d)\n", btnA.x, btnA.y, btnB.x, btnB.y, prize.x, prize.y);
     30     }
     31 };
     32 
     33 struct State {
     34     const Machine &m;
     35     int pressesA;
     36     int pressesB;
     37 };
     38 
     39 typedef std::vector<Machine> Data;
     40 
     41 template<typename T>
     42 T read_file(const std::string &path) {
     43     std::ifstream ifs(path, std::ios::binary);
     44     if (!ifs.is_open()) {
     45         throw std::runtime_error(path+":"+std::strerror(errno));
     46     }
     47     T buf;
     48     int lines = 0;
     49     while (1) {
     50         std::string str;
     51         std::getline(ifs, str);
     52         if (!str.empty()) {
     53             int c = lines % 4;
     54             if (c==0) {
     55                 Machine m;
     56                 m.btnA.fromStr(str);
     57                 buf.push_back(m);
     58             }
     59             if (c==1) buf.back().btnB.fromStr(str);
     60             if (c==2) buf.back().setPrize(str);
     61         }
     62         if (!ifs) break;
     63         lines++;
     64     }
     65     return buf;
     66 }
     67 
     68 void simulate(const Machine &m, int pA, int pB, std::vector<int> &out) {
     69     if (pA>100||pB>100) return;
     70     int curX = m.btnA.x*pA + m.btnB.x*pB;
     71     int curY = m.btnA.y*pA + m.btnB.y*pB;
     72     //std::printf("pA=%d, pB=%d, curX=%d, curY=%d\n", pA, pB, curX, curY);
     73     if (curX>m.prize.x||curY>m.prize.y) return;
     74     if (m.btnA.x*pA==m.prize.x&&m.btnB.y*pB==m.prize.y) {
     75         out.push_back(pA*3+pB);
     76     } else {
     77         simulate(m, ++pA, pB, out);
     78         simulate(m, pA, ++pB, out);
     79     }
     80 }
     81 
     82 int64_t part1(Data &input [[ maybe_unused ]]) {
     83     int64_t res = 0;
     84     for (auto &m:input) {
     85         m.print();
     86         std::vector<int> runs;
     87         simulate(m, 0, 0, runs);
     88         std::sort(runs.begin(), runs.end());
     89         std::printf("%ld successful results\n", runs.size());
     90     }
     91 
     92     return res;
     93 }
     94 int64_t part2(Data &input [[ maybe_unused ]]) {
     95     return 0;
     96 }
     97 
     98 int main(int argc, char **argv) {
     99     Performance perf;
    100     const std::string fname = argc>1 ? argv[1] : "test1.txt";
    101     std::cout << "AoC 2024 day 13 " << fname << std::endl;
    102     Data input = read_file<Data>(fname);
    103     std::cout << "part1: " << part1(input) << std::endl;
    104     std::cout << "part2: " << part2(input) << std::endl;
    105 
    106     return 0;
    107 }