Advertisement
Guest User

Advent of Code 2023 Day 10 Solution

a guest
Dec 10th, 2023
180
0
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
C++ 6.85 KB | Source Code | 0 0
  1. #include <bits/stdc++.h>
  2. using namespace std;
  3.  
  4. vector<string> read_lines(string file_name = "input.txt") {
  5.   vector<string> res;
  6.   string line;
  7.   ifstream file(file_name);
  8.   if (file.is_open()) {
  9.     while (getline(file, line)) {
  10.       res.push_back(line);
  11.     }
  12.     file.close();
  13.   }
  14.   return res;
  15. }
  16.  
  17. vector<string> split(string s, char c = ' ') {
  18.   vector<string> res;
  19.   string cur = "";
  20.   for (char ch : s) {
  21.     if (ch == c) {
  22.       if (!cur.empty())
  23.         res.push_back(cur);
  24.       cur = "";
  25.     } else {
  26.       cur += ch;
  27.     }
  28.   }
  29.   if (!cur.empty()) {
  30.     res.push_back(cur);
  31.   }
  32.   return res;
  33. }
  34.  
  35. string rltrim(string s, char c = ' ') {
  36.   int lo = -1, hi = -1;
  37.   for (int i = 0; i < (int)s.size(); i++) {
  38.     if (s[i] != c) {
  39.       lo = i;
  40.       break;
  41.     }
  42.   }
  43.   for (int i = (int)s.size() - 1; i >= 0; i--) {
  44.     if (s[i] != c) {
  45.       hi = i;
  46.       break;
  47.     }
  48.   }
  49.   if (lo != -1 and hi != -1) {
  50.     string res = "";
  51.     for (int i = lo; i <= hi; i++)
  52.       res += s[i];
  53.     return res;
  54.   }
  55.   return "";
  56. }
  57.  
  58. int64_t silver(vector<string> lines) {
  59.   int64_t ans = 0;
  60.   vector<string> a = lines;
  61.   const int n = (int)a.size(), m = (int)a[0].size();
  62.  
  63.   pair<int, int> src = {-1, -1};
  64.  
  65.   for (int i = 0; i < n; i++) {
  66.     for (int j = 0; j < m; j++) {
  67.       if (a[i][j] == 'S') {
  68.         src = {i, j};
  69.         break;
  70.       }
  71.     }
  72.     if (src != make_pair(-1, -1))
  73.       break;
  74.   }
  75.  
  76.   auto ok = [&](int x, int y) -> bool {
  77.     return 0 <= x and x < n and 0 <= y and y < m;
  78.   };
  79.  
  80.   auto moves = [&](int x, int y) -> vector<pair<int, int>> {
  81.     char c = a[x][y];
  82.     if (c == 'S') {
  83.       return {{0, 1}, {0, -1}, {1, 0}, {-1, 0}};
  84.     } else if (c == 'F') {
  85.       return {{0, 1}, {1, 0}};
  86.     } else if (c == 'L') {
  87.       return {{0, 1}, {-1, 0}};
  88.     } else if (c == 'J') {
  89.       return {{0, -1}, {-1, 0}};
  90.     } else if (c == '7') {
  91.       return {{0, -1}, {1, 0}};
  92.     } else if (c == '-') {
  93.       return {{0, -1}, {0, 1}};
  94.     } else if (c == '|') {
  95.       return {{1, 0}, {-1, 0}};
  96.     }
  97.     return {};
  98.   };
  99.  
  100.   auto possible = [&](int x, int y, int dx, int dy) -> bool {
  101.     if (!ok(x + dx, y + dy))
  102.       return false;
  103.     char c = a[x + dx][y + dy];
  104.     string s = "FLJ7-|";
  105.     bool ok = false;
  106.     for (char ch : s) {
  107.       if (ch == c)
  108.         ok = true;
  109.     }
  110.     if (ok) {
  111.       for (auto &[rdx, rdy] : moves(x + dx, y + dy)) {
  112.         if (dx == -rdx and dy == -rdy)
  113.           return true;
  114.       }
  115.     }
  116.     return false;
  117.   };
  118.  
  119.   auto [sx, sy] = src;
  120.   vector<vector<int64_t>> d(n, vector<int64_t>(m, -1));
  121.   queue<pair<int, int>> q;
  122.   d[sx][sy] = 0;
  123.   q.emplace(sx, sy);
  124.   while (!q.empty()) {
  125.     auto [ux, uy] = q.front();
  126.     ans = max(ans, d[ux][uy]);
  127.     q.pop();
  128.     for (auto &[dx, dy] : moves(ux, uy)) {
  129.       int vx = ux + dx, vy = uy + dy;
  130.       if (possible(ux, uy, dx, dy) and d[vx][vy] == -1) {
  131.         d[vx][vy] = d[ux][uy] + 1;
  132.         q.emplace(vx, vy);
  133.       }
  134.     }
  135.   }
  136.  
  137.   return ans;
  138. }
  139.  
  140. int64_t gold(vector<string> lines) {
  141.   int64_t ans = 0;
  142.   vector<string> a(2 * lines.size(), string(2 * lines[0].size(), '.'));
  143.   for (int i = 0; i < (int)lines.size(); i++) {
  144.     for (int j = 0; j < (int)lines[0].size(); j++) {
  145.       a[2 * i][2 * j] = lines[i][j];
  146.     }
  147.   }
  148.  
  149.   const int n = (int)a.size(), m = (int)a[0].size();
  150.  
  151.   auto ok = [&](int x, int y) -> bool {
  152.     return 0 <= x and x < n and 0 <= y and y < m;
  153.   };
  154.  
  155.   auto moves = [&](int x, int y) -> vector<pair<int, int>> {
  156.     char c = a[x][y];
  157.     if (c == 'S') {
  158.       return {{0, 1}, {0, -1}, {1, 0}, {-1, 0}};
  159.     } else if (c == 'F') {
  160.       return {{0, 1}, {1, 0}};
  161.     } else if (c == 'L') {
  162.       return {{0, 1}, {-1, 0}};
  163.     } else if (c == 'J') {
  164.       return {{0, -1}, {-1, 0}};
  165.     } else if (c == '7') {
  166.       return {{0, -1}, {1, 0}};
  167.     } else if (c == '-') {
  168.       return {{0, -1}, {0, 1}};
  169.     } else if (c == '|') {
  170.       return {{1, 0}, {-1, 0}};
  171.     }
  172.     return {};
  173.   };
  174.  
  175.   auto possible = [&](int x, int y, int dx, int dy) -> bool {
  176.     if (!ok(x + dx, y + dy))
  177.       return false;
  178.     char c = a[x + dx][y + dy];
  179.     string s = "SFLJ7-|";
  180.     bool ok = false;
  181.     for (char ch : s) {
  182.       if (ch == c)
  183.         ok = true;
  184.     }
  185.     if (ok) {
  186.       for (auto &[rdx, rdy] : moves(x + dx, y + dy)) {
  187.         if (dx == -rdx and dy == -rdy)
  188.           return true;
  189.       }
  190.     }
  191.     return false;
  192.   };
  193.  
  194.   for (int i = 0; i < n; i++) {
  195.     for (int j = 1; j < m; j += 2) {
  196.       if (possible(i, j, 0, -1) and possible(i, j, 0, 1))
  197.         a[i][j] = '-';
  198.  
  199.       if (possible(i, j, -1, 0) and possible(i, j, 1, 0))
  200.         a[i][j] = '|';
  201.     }
  202.   }
  203.   for (int j = 0; j < m; j++) {
  204.     for (int i = 1; i < n; i += 2) {
  205.       if (possible(i, j, 0, -1) and possible(i, j, 0, 1))
  206.         a[i][j] = '-';
  207.  
  208.       if (possible(i, j, -1, 0) and possible(i, j, 1, 0))
  209.         a[i][j] = '|';
  210.     }
  211.   }
  212.  
  213.   pair<int, int> src = {-1, -1};
  214.  
  215.   for (int i = 0; i < n; i++) {
  216.     for (int j = 0; j < m; j++) {
  217.       if (a[i][j] == 'S') {
  218.         src = {i, j};
  219.         break;
  220.       }
  221.     }
  222.     if (src != make_pair(-1, -1))
  223.       break;
  224.   }
  225.  
  226.   auto [sx, sy] = src;
  227.   vector<vector<int64_t>> d(n, vector<int64_t>(m, -1));
  228.   queue<pair<int, int>> q;
  229.   d[sx][sy] = 0;
  230.   q.emplace(sx, sy);
  231.   while (!q.empty()) {
  232.     auto [ux, uy] = q.front();
  233.     q.pop();
  234.     for (auto &[dx, dy] : moves(ux, uy)) {
  235.       int vx = ux + dx, vy = uy + dy;
  236.       if (possible(ux, uy, dx, dy) and d[vx][vy] == -1) {
  237.         d[vx][vy] = d[ux][uy] + 1;
  238.         q.emplace(vx, vy);
  239.       }
  240.     }
  241.   }
  242.  
  243.   function<void(int, int)> dfs = [&](int x, int y) -> void {
  244.     d[x][y] = 0;
  245.     for (auto &[dx, dy] : moves(sx, sy)) {
  246.       int vx = x + dx, vy = y + dy;
  247.       if (ok(vx, vy) and d[vx][vy] == -1) {
  248.         dfs(vx, vy);
  249.       }
  250.     }
  251.   };
  252.  
  253.   for (int i = 0; i < n; i++) {
  254.     int x = i, y = 0;
  255.     if (d[x][y] == -1)
  256.       dfs(x, y);
  257.     y = m - 1;
  258.     if (d[x][y] == -1)
  259.       dfs(x, y);
  260.   }
  261.  
  262.   for (int j = 0; j < m; j++) {
  263.     int x = 0, y = j;
  264.     if (d[x][y] == -1)
  265.       dfs(x, y);
  266.     x = n - 1;
  267.     if (d[x][y] == -1)
  268.       dfs(x, y);
  269.   }
  270.  
  271.   for (int i = 0; i < n; i++) {
  272.     for (int j = 0; j < m; j++) {
  273.       ans += (d[i][j] == -1);
  274.     }
  275.   }
  276.  
  277.   int res = 0;
  278.   for (int i = 0; i < n; i++) {
  279.     for (int j = 0; j < m; j++) {
  280.       vector<pair<int, int>> nxt = {
  281.           {i, j}, {i + 1, j + 1}, {i + 1, j}, {i, j + 1}};
  282.       int count = 0;
  283.       for (auto &[x, y] : nxt) {
  284.         if (ok(x, y)) {
  285.           count += (d[x][y] == -1);
  286.         }
  287.       }
  288.       if (count == 4) {
  289.         res++;
  290.         for (auto &[x, y] : nxt) {
  291.           d[x][y] = -2;
  292.         }
  293.       }
  294.     }
  295.   }
  296.   ans = res;
  297.  
  298.   return ans;
  299. }
  300.  
  301. int main() {
  302.   vector<string> lines = read_lines();
  303.   cout << silver(lines) << '\n';
  304.   cout << gold(lines) << '\n';
  305.   return 0;
  306. }
  307.  
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement