header_utils
Loading...
Searching...
No Matches
enum_flags.h
1#pragma once
2
3#if __cplusplus >= 201103L || defined(__cpp_constexpr)
4#define EF_CONSTEXPR constexpr
5#define EF_EXPLICITOP explicit
6#define EF_NOEXCEPT noexcept
7#if __has_cpp_attribute(nodiscard)
8#define EF_NODISCARD [[nodiscard]]
9#else
10#define EF_NODISCARD
11#endif
12#else
13#define EF_CONSTEXPR
14#define EF_EXPLICITOP
15#define EF_NOEXCEPT
16#define EF_NODISCARD
17#endif
18
19namespace ghassanpl
20{
21 template <typename RESULT_TYPE, typename ENUM_TYPE>
22 EF_CONSTEXPR RESULT_TYPE flag_bit(ENUM_TYPE e) EF_NOEXCEPT
23 {
24 return ((static_cast<RESULT_TYPE>(1) << static_cast<RESULT_TYPE>(e)));
25 }
26
27 template <typename ENUM_TYPE, typename VALUE_TYPE = unsigned long long>
29 {
31 typedef VALUE_TYPE value_type;
32
36
37 value_type bits;
38
39 EF_CONSTEXPR enum_flags() EF_NOEXCEPT : bits(0) {}
40 EF_CONSTEXPR enum_flags(const enum_flags& other) EF_NOEXCEPT : bits(other.bits) {};
41 EF_CONSTEXPR enum_flags& operator=(const enum_flags& other) EF_NOEXCEPT { bits = other.bits; return *this; }
42
43 EF_CONSTEXPR enum_flags(enum_type base_value) EF_NOEXCEPT : bits(flag_bit<VALUE_TYPE>(base_value)) {}
44 EF_CONSTEXPR explicit enum_flags(value_type value) EF_NOEXCEPT : bits(value) {}
45
47 EF_NODISCARD EF_CONSTEXPR static self_type from_bits(value_type val) EF_NOEXCEPT {
49 ret.bits = val;
50 return ret;
51 }
52
54 EF_NODISCARD EF_CONSTEXPR static self_type all() EF_NOEXCEPT { return self_type::from_bits(~static_cast<VALUE_TYPE>(0)); }
55
57 EF_NODISCARD EF_CONSTEXPR static self_type all(enum_type last) EF_NOEXCEPT { return self_type::from_bits(flag_bit<VALUE_TYPE>(last) | (flag_bit<VALUE_TYPE>(last) - 1)); }
58
60 EF_NODISCARD EF_CONSTEXPR static self_type none() EF_NOEXCEPT { return self_type(); }
61
63 EF_NODISCARD EF_CONSTEXPR bool is_set(enum_type flag) const EF_NOEXCEPT { return (bits & flag_bit<VALUE_TYPE>(flag)) != 0; }
64
66 EF_NODISCARD EF_CONSTEXPR bool contain(enum_type flag) const EF_NOEXCEPT { return this->is_set(flag); }
68 EF_NODISCARD EF_CONSTEXPR bool contains(enum_type flag) const EF_NOEXCEPT { return this->is_set(flag); }
69
71 EF_NODISCARD EF_CONSTEXPR bool are_any_set() const EF_NOEXCEPT { return bits != 0; }
72
75 EF_NODISCARD EF_CONSTEXPR bool are_any_set(self_type other) const EF_NOEXCEPT { return other.bits == 0 /* empty set */ || (bits & other.bits) != 0; }
76
78 EF_NODISCARD EF_CONSTEXPR bool are_all_set(self_type other) const EF_NOEXCEPT { return (bits & other.bits) == other.bits; }
79
80 EF_CONSTEXPR EF_EXPLICITOP operator bool() const EF_NOEXCEPT { return bits != 0; }
81
83 EF_NODISCARD EF_CONSTEXPR enum_type to_enum_type() const EF_NOEXCEPT { return static_cast<enum_type>(bits); }
84
86 EF_CONSTEXPR self_type& set(enum_type e) EF_NOEXCEPT { bits |= flag_bit<VALUE_TYPE>(e); return *this; }
88 EF_CONSTEXPR self_type& set(self_type other) EF_NOEXCEPT { bits |= other.bits; return *this; }
89
91 EF_CONSTEXPR self_type& unset(enum_type e) EF_NOEXCEPT { bits &= ~flag_bit<VALUE_TYPE>(e); return *this; }
93 EF_CONSTEXPR self_type& unset(self_type other) EF_NOEXCEPT { bits &= ~other.bits; return *this; }
94
96 EF_CONSTEXPR self_type& toggle(enum_type e) EF_NOEXCEPT { bits ^= flag_bit<VALUE_TYPE>(e); return *this; }
98 EF_CONSTEXPR self_type& toggle(self_type other) EF_NOEXCEPT { bits ^= other.bits; return *this; }
99
101 EF_CONSTEXPR self_type& set_to(enum_type e, bool val) EF_NOEXCEPT
102 {
103 if (val) bits |= flag_bit<VALUE_TYPE>(e); else bits &= ~flag_bit<VALUE_TYPE>(e);
104 return *this;
105 }
106
108 EF_CONSTEXPR self_type& set_to(self_type other, bool val) EF_NOEXCEPT
109 {
110 if (val) bits |= other.bits; else bits &= ~other.bits;
111 return *this;
112 }
113
115 EF_NODISCARD EF_CONSTEXPR self_type but_only(self_type flags) const EF_NOEXCEPT { return self_type::from_bits(bits & flags.bits); }
116
118 EF_NODISCARD EF_CONSTEXPR self_type intersected_with(self_type flags) const EF_NOEXCEPT { return self_type::from_bits(bits & flags.bits); }
119
120 EF_NODISCARD EF_CONSTEXPR self_type operator+(enum_type flag) const EF_NOEXCEPT { return self_type::from_bits(bits | flag_bit<VALUE_TYPE>(flag)); }
121 EF_NODISCARD EF_CONSTEXPR self_type operator-(enum_type flag) const EF_NOEXCEPT { return self_type::from_bits(bits & ~flag_bit<VALUE_TYPE>(flag)); }
122
123 EF_NODISCARD EF_CONSTEXPR self_type operator+(self_type flags) const EF_NOEXCEPT { return self_type::from_bits(bits | flags.bits); }
124 EF_NODISCARD EF_CONSTEXPR self_type operator-(self_type flags) const EF_NOEXCEPT { return self_type::from_bits(bits & ~flags.bits); }
125
126 EF_CONSTEXPR self_type& operator+=(enum_type flag) EF_NOEXCEPT { bits |= flag_bit<VALUE_TYPE>(flag); return *this; }
127 EF_CONSTEXPR self_type& operator-=(enum_type flag) EF_NOEXCEPT { bits &= ~flag_bit<VALUE_TYPE>(flag); return *this; }
128
129 EF_CONSTEXPR self_type& operator+=(self_type flags) EF_NOEXCEPT { bits |= flags.bits; return *this; }
130 EF_CONSTEXPR self_type& operator-=(self_type flags) EF_NOEXCEPT { bits &= ~flags.bits; return *this; }
131
132 EF_CONSTEXPR bool operator==(self_type other) const EF_NOEXCEPT { return bits == other.bits; }
133 EF_CONSTEXPR bool operator!=(self_type other) const EF_NOEXCEPT { return bits != other.bits; }
134
135 EF_CONSTEXPR bool operator<(enum_flags const& other) const EF_NOEXCEPT { return bits < other.bits; }
136 EF_CONSTEXPR bool operator>(enum_flags const& other) const EF_NOEXCEPT { return bits > other.bits; }
137 EF_CONSTEXPR bool operator<=(enum_flags const& other) const EF_NOEXCEPT { return bits <= other.bits; }
138 EF_CONSTEXPR bool operator>=(enum_flags const& other) const EF_NOEXCEPT { return bits >= other.bits; }
139
140 EF_CONSTEXPR bool empty() const EF_NOEXCEPT { return bits == 0; }
141 EF_CONSTEXPR void clear() EF_NOEXCEPT { bits = 0; }
142 };
143}
144#undef EF_CONSTEXPR
145#undef EF_EXPLICITOP
146#undef EF_NOEXCEPT
147#undef EF_NODISCARD
constexpr auto bit_count
Equal to the number of bits in the type.
Definition bits.h:33
Primary namespace for everything in this library.
Definition align+rec2.h:10
A (constexpr) value struct that represents a set of bits mapped to an enum (implemented as a bitset)
Definition enum_flags.h:29
EF_CONSTEXPR self_type & set_to(self_type other, bool val) EF_NOEXCEPT
Sets the flags in the other set to val
Definition enum_flags.h:108
EF_NODISCARD static EF_CONSTEXPR self_type from_bits(value_type val) EF_NOEXCEPT
Creates the enum_flags set from the given underlying bits.
Definition enum_flags.h:47
EF_CONSTEXPR self_type & unset(self_type other) EF_NOEXCEPT
Unsets the flags in the other set.
Definition enum_flags.h:93
EF_NODISCARD static EF_CONSTEXPR self_type all(enum_type last) EF_NOEXCEPT
Returns a value with all bits set, up to and including the last
Definition enum_flags.h:57
EF_NODISCARD EF_CONSTEXPR enum_type to_enum_type() const EF_NOEXCEPT
Returns the underlying value representing this set cast to the enum_type.
Definition enum_flags.h:83
EF_NODISCARD static EF_CONSTEXPR self_type all() EF_NOEXCEPT
Returns a value with all bits set (including the ones not in the enum, if any)
Definition enum_flags.h:54
EF_CONSTEXPR self_type & unset(enum_type e) EF_NOEXCEPT
Unsets the given flag.
Definition enum_flags.h:91
EF_CONSTEXPR self_type & toggle(self_type other) EF_NOEXCEPT
Toggles the flags in the other set.
Definition enum_flags.h:98
EF_NODISCARD EF_CONSTEXPR bool are_all_set(self_type other) const EF_NOEXCEPT
Returns whether or not all of the flags in the other set are set.
Definition enum_flags.h:78
EF_CONSTEXPR self_type & set(enum_type e) EF_NOEXCEPT
Sets the given flag.
Definition enum_flags.h:86
EF_NODISCARD EF_CONSTEXPR bool contain(enum_type flag) const EF_NOEXCEPT
Same as is_set.
Definition enum_flags.h:66
EF_NODISCARD EF_CONSTEXPR bool are_any_set() const EF_NOEXCEPT
Returns whether or not any of the given flags are set.
Definition enum_flags.h:71
EF_NODISCARD EF_CONSTEXPR bool are_any_set(self_type other) const EF_NOEXCEPT
Returns whether or not any of the flags in the other set are set.
Definition enum_flags.h:75
EF_NODISCARD EF_CONSTEXPR self_type intersected_with(self_type flags) const EF_NOEXCEPT
Returns a value with our bits from only the flags that are also set in flags (an intersection)
Definition enum_flags.h:118
EF_CONSTEXPR self_type & set_to(enum_type e, bool val) EF_NOEXCEPT
Sets the given flags to val
Definition enum_flags.h:101
EF_NODISCARD EF_CONSTEXPR self_type but_only(self_type flags) const EF_NOEXCEPT
Returns a value with our bits from only the flags that are also set in flags (an intersection)
Definition enum_flags.h:115
ENUM_TYPE enum_type
Type of the enum that is the source of the flags.
Definition enum_flags.h:34
EF_CONSTEXPR self_type & set(self_type other) EF_NOEXCEPT
Sets the flags in the other
Definition enum_flags.h:88
EF_NODISCARD EF_CONSTEXPR bool is_set(enum_type flag) const EF_NOEXCEPT
Returns whether or not flag is set.
Definition enum_flags.h:63
EF_CONSTEXPR self_type & toggle(enum_type e) EF_NOEXCEPT
Toggles the given flag.
Definition enum_flags.h:96
EF_NODISCARD static EF_CONSTEXPR self_type none() EF_NOEXCEPT
Returns a value with none of the bits set.
Definition enum_flags.h:60
VALUE_TYPE value_type
The underlying integral value type that holds the bits representing the flags.
Definition enum_flags.h:31
EF_NODISCARD EF_CONSTEXPR bool contains(enum_type flag) const EF_NOEXCEPT
Same as is_set.
Definition enum_flags.h:68