ARTS 2.5.10 (git: 2f1c442c)
enums.h
Go to the documentation of this file.
1#ifndef enums_h
2#define enums_h
3
4#include <algorithm>
5#include <array>
6#include <iostream>
7#include <sstream>
8#include <string>
9#include <string_view>
10
11#include "debug.h"
12#include "nonstd.h"
13
21template <typename EnumType> constexpr bool good_enum(EnumType x) noexcept {
22 return std::size_t(x) < std::size_t(EnumType::FINAL);
23}
24
33template <typename EnumType>
34constexpr std::array<std::string_view, size_t(EnumType::FINAL)>
35enum_strarray(const std::string_view strchars) noexcept {
36 std::array<std::string_view, size_t(EnumType::FINAL)> out;
37
38 // Find the start
39 std::string_view::size_type N0 = 0;
40
41 // Set all the values
42 for (auto &str : out) {
43 // Find a comma but never look beyond the end of the string
44 const std::string_view::size_type N1 =
45 std::min(strchars.find(',', N0), strchars.size());
46
47 // Set the string between start and the length of the string
48 str = strchars.substr(N0, N1 - N0);
49
50 // Remove spaces at the beginning and at the end of the string
51 while (nonstd::isspace(str.front()))
52 str.remove_prefix(1);
53 while (nonstd::isspace(str.back()))
54 str.remove_suffix(1);
55
56 // Set the new start for the next iteration
57 N0 = N1 + 1;
58 }
59
60 return out;
61}
62
63template <typename EnumType>
64constexpr std::array<std::string_view, 0> enum_strarray() noexcept {
65 return {};
66}
67
74template <typename EnumType>
75constexpr std::array<EnumType, size_t(EnumType::FINAL)>
76enum_typarray() noexcept {
77 std::array<EnumType, size_t(EnumType::FINAL)> out{};
78 for (size_t i = 0; i < size_t(EnumType::FINAL); i++)
79 out[i] = EnumType(i);
80 return out;
81}
82
89template <typename EnumType, typename... Messages>
90constexpr void check_enum_error(EnumType type, Messages... args) {
91 ARTS_USER_ERROR_IF(not good_enum(type), args...)
92}
93
142#define ENUMCLASS(ENUMTYPE, TYPE, ...) \
143 enum class ENUMTYPE : TYPE { __VA_OPT__(__VA_ARGS__, ) FINAL }; \
144 \
145 namespace enumstrs { \
146 constexpr auto ENUMTYPE##Names = \
147 enum_strarray<ENUMTYPE>(__VA_OPT__(#__VA_ARGS__)); \
148 } \
149 \
150 namespace enumtyps { \
151 [[maybe_unused]] constexpr auto ENUMTYPE##Types = enum_typarray<ENUMTYPE>(); \
152 } \
153 \
154 constexpr std::string_view toString(ENUMTYPE x) noexcept { \
155 if (good_enum(x)) \
156 return enumstrs::ENUMTYPE##Names[(TYPE)x]; \
157 return "BAD " #ENUMTYPE; \
158 } \
159 \
160 constexpr ENUMTYPE to##ENUMTYPE(const std::string_view x) noexcept { \
161 for (TYPE i = 0; i < (TYPE)ENUMTYPE::FINAL; i++) \
162 if (enumstrs::ENUMTYPE##Names[i] == x) \
163 return ENUMTYPE(i); \
164 return ENUMTYPE::FINAL; \
165 } \
166 \
167 constexpr ENUMTYPE to##ENUMTYPE##OrThrow(const std::string_view x) { \
168 const ENUMTYPE out = to##ENUMTYPE(x); \
169 check_enum_error(out, "Cannot understand argument: \"", x, \
170 "\"\n" \
171 "Valid " #ENUMTYPE \
172 " options are: [" __VA_OPT__(#__VA_ARGS__) "]"); \
173 return out; \
174 } \
175 \
176 inline std::ostream &operator<<(std::ostream &os, const ENUMTYPE x) { \
177 return os << toString(x); \
178 } \
179 \
180 inline std::istream &operator>>(std::istream &is, ENUMTYPE &x) { \
181 std::string val; \
182 is >> val; \
183 x = to##ENUMTYPE##OrThrow(val); \
184 return is; \
185 }
186
187#endif // enums_h
Helper macros for debugging.
#define ARTS_USER_ERROR_IF(condition,...)
Definition: debug.h:153
constexpr std::array< EnumType, size_t(EnumType::FINAL)> enum_typarray() noexcept
A list of all enum types by index-conversion.
Definition: enums.h:76
constexpr std::array< std::string_view, 0 > enum_strarray() noexcept
Definition: enums.h:64
constexpr void check_enum_error(EnumType type, Messages... args)
Checks if the enum class type is good and otherwise throws an error message composed by variadic inpu...
Definition: enums.h:90
constexpr bool good_enum(EnumType x) noexcept
Checks if the enum number is good.
Definition: enums.h:21
constexpr int isspace(int ch) noexcept
Returns 1 if x is a standard space-character.
Definition: nonstd.h:39
#define N1
Definition: rng.cc:273