Skip to content

Commit d10f2b1

Browse files
author
bt
committed
Day 25 part1
1 parent d7533e5 commit d10f2b1

File tree

2 files changed

+125
-0
lines changed

2 files changed

+125
-0
lines changed

CMakeLists.txt

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -30,6 +30,7 @@ add_challenge(day17)
3030
add_challenge(day18)
3131
add_challenge(day19)
3232
add_challenge(day24)
33+
add_challenge(day25)
3334

3435
add_custom_command(TARGET day1
3536
COMMAND ${CMAKE_COMMAND} -E create_symlink "${CMAKE_CURRENT_SOURCE_DIR}/data" "./data"

src/day25.cpp

Lines changed: 124 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,124 @@
1+
#include "common_headers.hpp"
2+
3+
using Heights = std::vector<size_t>;
4+
5+
struct LocksAndKeys final
6+
{
7+
size_t lockHeight{7};
8+
std::vector<Heights> locks;
9+
std::vector<Heights> keys;
10+
};
11+
12+
13+
[[nodiscard]] size_t solveFirstPart(const LocksAndKeys& locksAndKeys)
14+
{
15+
size_t count{};
16+
for(const auto& lock : locksAndKeys.locks) {
17+
for(const auto& key : locksAndKeys.keys) {
18+
if(lock.size() != key.size()) {
19+
throw std::logic_error{"sizes of lock and key differ"};
20+
}
21+
bool fit{true};
22+
for(size_t i = 0; i < lock.size(); ++i) {
23+
fit = fit && (lock[i] + key[i] <= locksAndKeys.lockHeight);
24+
}
25+
count += fit;
26+
}
27+
}
28+
return count;
29+
}
30+
31+
[[nodiscard]] size_t parseHeights(const std::vector<std::string>& inputVec, size_t beginInputId, Heights& heights)
32+
{
33+
size_t inputId{beginInputId};
34+
heights.reserve(inputVec[0].size());
35+
for(size_t column = 0; column < inputVec[0].size(); ++column) {
36+
auto row = inputId;
37+
size_t height{};
38+
while(row < inputVec.size() && !inputVec[row].empty()) {
39+
height += (inputVec[row][column] == '#');
40+
++row;
41+
}
42+
heights.push_back(height);
43+
}
44+
45+
while(inputId < inputVec.size() && !inputVec[inputId].empty()) ++inputId;
46+
++inputId; //< skip empty line
47+
return inputId;
48+
}
49+
50+
[[nodiscard]] size_t parseLocks(const std::vector<std::string>& inputVec, size_t beginInputId, LocksAndKeys& locksAndKeys)
51+
{
52+
size_t inputId{beginInputId};
53+
while(inputId < inputVec.size() && inputVec[inputId][0] == '#') {
54+
locksAndKeys.locks.emplace_back();
55+
inputId = parseHeights(inputVec, inputId, locksAndKeys.locks.back());
56+
57+
if(locksAndKeys.locks.back().empty()) {
58+
locksAndKeys.locks.back().pop_back();
59+
}
60+
}
61+
return inputId;
62+
}
63+
64+
[[nodiscard]] size_t parseKeys(const std::vector<std::string>& inputVec, size_t beginInputId, LocksAndKeys& locksAndKeys)
65+
{
66+
size_t inputId{beginInputId};
67+
while(inputId < inputVec.size() && inputVec[inputId][0] == '.') {
68+
locksAndKeys.keys.emplace_back();
69+
inputId = parseHeights(inputVec, inputId, locksAndKeys.keys.back());
70+
71+
if(locksAndKeys.keys.back().empty()) {
72+
locksAndKeys.keys.back().pop_back();
73+
}
74+
}
75+
return inputId;
76+
}
77+
78+
[[nodiscard]] LocksAndKeys parseInput(const std::vector<std::string>& inputVec)
79+
{
80+
LocksAndKeys locksAndKeys;
81+
size_t inputId{};
82+
while(inputId < inputVec.size()) {
83+
inputId = parseLocks(inputVec, inputId, locksAndKeys);
84+
inputId = parseKeys(inputVec, inputId, locksAndKeys);
85+
}
86+
87+
return locksAndKeys;
88+
}
89+
90+
void printHelp()
91+
{
92+
std::cerr << "\nUsage:\n"
93+
<< "The program requires 2 args: (part1, part2) and the path to the file."
94+
<< "\nFor example, ./day7 part1 data/day7.txt";
95+
}
96+
97+
int main(int argc, char* argv[])
98+
{
99+
if(argc != 3) {
100+
printHelp();
101+
return 1;
102+
}
103+
104+
std::string_view task{argv[1]};
105+
if(task != "part1" && task != "part2") {
106+
std::cerr << "\nfirst arg can be either `part1` or `part2`\n";
107+
printHelp();
108+
return 1;
109+
}
110+
111+
std::vector<std::string> inputVec;
112+
readInput(argv[2], std::back_inserter(inputVec));
113+
114+
auto locksAndKeys = parseInput(inputVec);
115+
116+
if(task == "part1") {
117+
std::cout << solveFirstPart(locksAndKeys);
118+
}
119+
else {
120+
// std::cout << solveSecondPart(program);
121+
}
122+
123+
return 0;
124+
}

0 commit comments

Comments
 (0)