main.cpp (2146B)
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 10 struct Report { 11 std::vector<int> levels; 12 Report(std::string str) { 13 std::istringstream ss(str); 14 for (std::string s; std::getline(ss, s, ' ');) { 15 levels.push_back(std::stoi(s)); 16 } 17 } 18 bool is_safe() { 19 return is_safe(levels); 20 } 21 bool is_safe(std::vector<int> levels) { 22 int sign = 0; 23 for (int i=1; i<(int)levels.size(); ++i) { 24 int diff = levels[i]-levels[i-1]; 25 int adiff = std::abs(diff); 26 if (adiff<1||adiff>3) return false; 27 if (sign==0) sign=diff/adiff; 28 if (sign!=0&&sign!=diff/adiff) return false; 29 } 30 return true; 31 } 32 bool is_safe2() { 33 if (is_safe()) return true; 34 for (int i=0; i<(int)levels.size(); ++i) { 35 auto levels2 = levels; 36 auto iter = levels2.begin()+i; 37 levels2.erase(iter); 38 if (is_safe(levels2)) return true; 39 } 40 return false; 41 } 42 }; 43 44 typedef std::vector<Report> Data; 45 46 template<typename T> 47 T read_file(const std::string &path) { 48 std::ifstream ifs(path, std::ios::binary); 49 if (!ifs.is_open()) { 50 throw std::runtime_error(path+":"+std::strerror(errno)); 51 } 52 T buf; 53 while (1) { 54 std::string str; 55 std::getline(ifs, str); 56 if (!str.empty()) buf.push_back(Report(str)); 57 if (!ifs) break; 58 } 59 return buf; 60 } 61 62 int part1(Data &input) { 63 int ret = 0; 64 for (auto &r : input) { 65 if (r.is_safe()) ++ret; 66 } 67 return ret; 68 } 69 int part2(Data &input) { 70 int ret = 0; 71 for (auto &r : input) { 72 if (r.is_safe2()) ++ret; 73 } 74 return ret; 75 } 76 77 int main(int argc, char **argv) { 78 const std::string fname = argc>1 ? argv[1] : "test1.txt"; 79 std::cout << "AoC 2024 day 02 " << fname << std::endl; 80 Data input = read_file<Data>(fname); 81 std::cout << "part1: " << part1(input) << std::endl; 82 std::cout << "part2: " << part2(input) << std::endl; 83 84 return 0; 85 }