diff options
-rw-r--r-- | 2023/flake.nix | 7 | ||||
-rw-r--r-- | 2023/include/util.h | 92 |
2 files changed, 96 insertions, 3 deletions
diff --git a/2023/flake.nix b/2023/flake.nix index ddf0408..9971fc1 100644 --- a/2023/flake.nix +++ b/2023/flake.nix | |||
@@ -56,7 +56,7 @@ | |||
56 | #include <iostream> | 56 | #include <iostream> |
57 | #include <fstream> | 57 | #include <fstream> |
58 | 58 | ||
59 | int main(void) | 59 | int main(int argc, char* argv[]) |
60 | { | 60 | { |
61 | int answer{}; | 61 | int answer{}; |
62 | 62 | ||
@@ -81,6 +81,7 @@ | |||
81 | 81 | ||
82 | cat << EOF >> Makefile | 82 | cat << EOF >> Makefile |
83 | CXXFLAGS := -std=c++17 | 83 | CXXFLAGS := -std=c++17 |
84 | CPPFLAGS := -I../include | ||
84 | EXE := part1 part2 | 85 | EXE := part1 part2 |
85 | 86 | ||
86 | .PHONY: all clean configure | 87 | .PHONY: all clean configure |
@@ -91,13 +92,13 @@ | |||
91 | bear -- \$(MAKE) all | 92 | bear -- \$(MAKE) all |
92 | 93 | ||
93 | %.o: %.cpp | 94 | %.o: %.cpp |
94 | \$(CXX) -c \$(CXXFLAGS) $< -o $@ | 95 | \$(CXX) -c \$(CPPFLAGS) \$(CXXFLAGS) \$< -o \$@ |
95 | 96 | ||
96 | clean: | 97 | clean: |
97 | rm -rf \$(EXE) src/*.o compile_commands.json | 98 | rm -rf \$(EXE) src/*.o compile_commands.json |
98 | 99 | ||
99 | %: src/%.o | 100 | %: src/%.o |
100 | \$(CXX) $^ -o $@ | 101 | \$(CXX) \$^ -o \$@ |
101 | EOF | 102 | EOF |
102 | ''; | 103 | ''; |
103 | } | 104 | } |
diff --git a/2023/include/util.h b/2023/include/util.h new file mode 100644 index 0000000..1b5f1c5 --- /dev/null +++ b/2023/include/util.h | |||
@@ -0,0 +1,92 @@ | |||
1 | #ifndef UTIL_H | ||
2 | #define UTIL_H | ||
3 | |||
4 | #include <algorithm> | ||
5 | #include <cstring> | ||
6 | #include <stdexcept> | ||
7 | #include <string> | ||
8 | |||
9 | namespace util | ||
10 | { | ||
11 | |||
12 | /* TODO */ | ||
13 | constexpr char SPACE[] = " "; | ||
14 | constexpr char COLON[] = ":"; | ||
15 | constexpr char SEMICOLON[] = ";"; | ||
16 | |||
17 | inline void trim(std::string& str) | ||
18 | { | ||
19 | str.erase(str.begin(), std::find_if_not(str.cbegin(), str.cend(), ::isspace)); | ||
20 | str.erase(std::find_if_not(str.crbegin(), str.crend(), ::isspace).base(), str.end()); | ||
21 | } | ||
22 | |||
23 | template<const char* delim, typename Accumulate> | ||
24 | void accumulate(const std::string& str, Accumulate acc) | ||
25 | { | ||
26 | size_t pos{}; | ||
27 | std::string elem; | ||
28 | |||
29 | while ((pos = str.find(delim)) != std::string::npos) { | ||
30 | auto sub = str.substr(0, pos); | ||
31 | trim(sub); | ||
32 | acc(sub); | ||
33 | pos += std::strlen(delim); | ||
34 | } | ||
35 | } | ||
36 | /* ---- */ | ||
37 | |||
38 | /** @brief Discard element from stream by type. | ||
39 | * | ||
40 | * @tparam T the type of the element to discard. | ||
41 | * @param stream the input stream. | ||
42 | * | ||
43 | * @return the input stream. | ||
44 | */ | ||
45 | template<typename T, typename CharT, typename Traits> | ||
46 | std::basic_istream<CharT, Traits>& skip(std::basic_istream<CharT, Traits>& stream) | ||
47 | { | ||
48 | T discard; | ||
49 | return stream >> discard; | ||
50 | } | ||
51 | |||
52 | /** @brief Skip token in stream. | ||
53 | * | ||
54 | * @tparam keyword the token to skip. | ||
55 | * @param stream the input stream. | ||
56 | * | ||
57 | * @return the input stream. | ||
58 | * | ||
59 | * @note The token needs to be declared as a `const char[]`, but normally, | ||
60 | * string literals are `const char*`. | ||
61 | * | ||
62 | * ```cpp | ||
63 | * constexpr char RESULT[] = "Result:"; | ||
64 | * | ||
65 | * int main(int argc, char* argv[]) | ||
66 | * { | ||
67 | * int res; | ||
68 | * std::istringstream in{ "Result: 42"} | ||
69 | * in >> skip<RESULT> >> res; | ||
70 | * | ||
71 | * // ... | ||
72 | * | ||
73 | * return 0 | ||
74 | * } | ||
75 | * ``` | ||
76 | */ | ||
77 | template<const char* keyword, typename CharT, typename Traits> | ||
78 | std::basic_istream<CharT, Traits>& skip(std::basic_istream<CharT, Traits>& stream) | ||
79 | { | ||
80 | std::string word; | ||
81 | stream >> word; | ||
82 | if (word != keyword) | ||
83 | { | ||
84 | throw std::invalid_argument("Malformed input"); | ||
85 | } | ||
86 | |||
87 | return stream; | ||
88 | } | ||
89 | |||
90 | } // namespace util | ||
91 | |||
92 | #endif //UTIL_H | ||